Hi Prakash, I see a system crash if I do freemsg. Following is the crash analysis
kernel memory allocator: buffer modified after being freed modification occurred at offset 0x70 (0xdeadbeefdeadbeef replaced by 0xaddebeefaddebeef) buffer=ffffffff91266700 bufctl=ffffffff9127c870 cache: streams_dblk_80 previous transaction on buffer ffffffff91266700: thread=fffffe80000adc80 time=T-0.000008601 slab=ffffffff83214890 cache: streams_dblk_80 kmem_cache_free_debug+f4 kmem_cache_free+43 dblk_lastfree+39 freemsg+7e pwise_appendto_payload+1f3 // Hook function pfil_precheck+cd2 pfilmodrput+395 putnext+1f1 gld_passon+b3 gld_sendup+fa gld_recv_tagged+175 ri_ste_def+363ed6eb rtls_receive+1f6 rtls_gld_intr+dc panic[cpu0]/thread=fffffe80000adc80: kernel heap corruption detected fffffe80000ad500 fffffffffb95e318 (ffffffff91268500, fffffffff) fffffe80000ad550 genunix:kmem_cache_alloc_debug+262 () fffffe80000ad580 genunix:kmem_cache_alloc+6f () fffffe80000ad5b0 genunix:allocb+77 () fffffe80000ad6e0 udp:udp_rput+853 () fffffe80000ad740 unix:putnext+1f1 () fffffe80000ad7f0 ip:ip_udp_input+632 () fffffe80000ad870 ip:ip_rput+6e1 () fffffe80000ad8d0 unix:putnext+1f1 () fffffe80000ad950 pfil:pfilmodrput+3e5 () fffffe80000ad9b0 unix:putnext+1f1 () fffffe80000ad9f0 gld:gld_passon+b3 () fffffe80000ada50 gld:gld_sendup+fa () fffffe80000adb70 gld:gld_recv_tagged+175 () fffffe80000adb80 gld:ri_ste_def+363ed6eb () fffffe80000adbd0 rtls:rtls_receive+1f6 () fffffe80000adc00 rtls:rtls_gld_intr+dc () fffffe80000adc10 gld:ri_ste_def+363ed507 () fffffe80000adc60 unix:av_dispatch_autovect+6a () Whereas if I don't do freemsg atall the code run's fine. Thanks, Sachin On Wed, 12 Apr 2006 00:32:31 +0530, Prakash Jalan <Prakash.Jalan at Sun.COM> wrote: > >> At present I am creating a new mblk copying the original IP,UDP >> packets + new data >> in new mblk, updating the length and checksums, then I freemsg() the >> original >> mblk at **mp and make mp point at the newly created mblk. I know this >> is not the correct way of doing as someone else maybe be pointing at >> original *mp. > > oh! don't worry about doing freemsg(). You are releasing your reference > on the message by calling freemsg() which is perfectly fine. freemsg() > internally takes care of other references by not freeing the dblk > if the reference count is greater than 1. > > I see an issue with your code though. A message is defined as chain > of message blocks (mblk_t) connected via b_cont field. For your case, > a single UDP packet could be spanned over multiple mblks connected > by b_cont field (still it would be single message). Your code looks > at the first mblk only and assume it contains the full packet, > which may not be the case. You should loop through the chain > and append your data at the last mblk of the message. > > b_next and b_prev are used to chain _messages_ together. > > Following diagram will help: > > message A mblk_A1.b_cont ---> mblk_A2.b_cont ---> mblk_A3.b_cont > > A | b_next > b_prev | V > > message B mblk_B1.b_cont ---> mblk_B2.b_cont ---> mblk_B3.b_cont > > A | b_next > b_prev | V > > message C mblk_C1.b_cont ---> mblk_C2.b_cont ---> mblk_C3.b_cont > > > prakah > >> Here is the code snip >> pfil_hook_function (...) >> { >> struct udphdr *oldudp,*udp; >> u_short sz,newlen; >> mblk_t *m; >> struct ip *ip,*oldip; >> char data[6] = {0}; >> int datalen = 6 ; >> oldip = (struct ip *)((*mp)->b_rptr) ; >> oldudp = (char *)oldip + hlen ; >> newlen = ntohs(oldudp->uh_ulen) + datalen; >> sz = hlen + newlen; >> if ((m = (mblk_t *)allocb((size_t)sz, BPRI_HI)) == NULL) { >> return 0; >> } >> MTYPE(m) = M_DATA; >> m->b_wptr = m->b_rptr + sz; >> bzero((char *)m->b_rptr, (size_t)sz); >> udp = (struct udp *)(m->b_rptr + hlen); >> bcopy(oldudp,udp,ntohs(oldudp->uh_ulen)); >> bcopy(data,(char *)udp + ntohs(oldudp->uh_ulen),datalen); >> ip = (struct ip *)m->b_rptr; >> bcopy(oldip,ip,hlen); >> ip->ip_len = htons(oldip->ip_len + datalen); >> ip->ip_sum = 0 ; >> ip->ip_sum = my_ip_checksum(ip, hlen) ; >> udp->uh_ulen = htons(newlen) ; >> udp->uh_sum = 0 ; >> udp->uh_sum = my_udp_checksum(ip->ip_dst.s_addr, >> >> ip->ip_src.s_addr,udp->uh_ulen,udp, >> newlen); >> m->b_prev = (*mp)->b_prev ; >> m->b_next = (*mp)->b_next ; >> m->b_cont = (*mp)->b_cont ; >> freemsg(*mp); >> *mp = m; >> return 0; >> } >> Any suggestions, or a better way of doing this ? >> Thanks, >> -Sachin >> _______________________________________________ >> ug-bosug mailing list >> List-Unsubscribe: mailto:ug-bosug-unsubscribe at opensolaris.org >> List-Owner: mailto:ug-bosug-owner at opensolaris.org >> List-Archives: http://www.opensolaris.org/jive/forum.jspa?forumID=54 > > _______________________________________________ > ug-bosug mailing list > List-Unsubscribe: mailto:ug-bosug-unsubscribe at opensolaris.org > List-Owner: mailto:ug-bosug-owner at opensolaris.org > List-Archives: http://www.opensolaris.org/jive/forum.jspa?forumID=54 -- Sachin Shelar Software Engineer S7 Software Solutions