The NF_ITERATE () function traverses a given linked list by I, and is processed in a given packet call list node. 335 static unsigned int nf_iterate (struct list_head * head, 336 struct sk_buff ** skb, 337 int hook, 338 const struct net_device * indev, 339 const struct net_device * outdev, 340 struct list_head ** i, 341 int (* okfn) ( Struct SK_BUFF *)) 342 {for loop completes traversal operation. When the HOOK function in the adjoin point is used, the corresponding processing is performed according to the return value. If the return value of the hook function is NF_QUEUE, NF_STOLEN, NF_DROP, the function returns the value; if the return value is NF_REPEAT, jump to the previous node to continue processing; if it is other value, continue processing by the next node. If the entire linked list is complete, the return value is not the above four values, then return NF_ACCEPT. 343 for (* i = (* i) -> next; * i! = Head; * i = (* i) -> next) {344 struct nf_hook_ops * elem = (struct nf_hook_ops *) * i; 345 Switch (ELEM -> hook (hook, skb, indev, outdev, okfn)) {346 case NF_QUEUE: 347 return NF_QUEUE; 348 349 case NF_STOLEN: 350 return NF_STOLEN; 351 352 case NF_DROP: 353 return NF_DROP; 354 355 case NF_REPEAT: 356 * i = (* i) -> prev; 357 Break; 358 359 #ifdef config_netfilter_debug 360 case nf_accept: 361 Break; 362 363 Default: 364 NFDebug ("Evil Return FROM% P (% U) ./ n", 365 elem-> Hook, hook; 366 #ENDIF 367} 368} 369 return nf_accept; 370} 371 is a queue registration process function. When registering is to register only a handler, if a given protocol has been registered, an error message is returned. Since queue_handler is a global structural variable, it is necessary to lock when registering and deleting. 372 int nf_register_queue_handler (int pf, nf_queue_outfn_t outfn, void * data) 373 {374 int ret; 375 376 br_write_lock_bh (BR_NETPROTO_LOCK); 377 if (queue_handler [pf] .outfn) 378 ret = -EBUSY; 379 else {380 queue_handler [pf ] .outfn = outfn; 381 queue_handler [pf] .data = data; 382 ret = 0; 383} 384 br_write_unlock_bh (BR_NETPROTO_LOCK); 385 386 return ret; 387} 388 389 / * The caller must flush their queue before this * / Delete the queue processing function of the given protocol.
390 int nf_unregister_queue_handler (int pf) 391 {392 br_write_lock_bh (BR_NETPROTO_LOCK); 393 queue_handler [pf] .outfn = NULL; 394 queue_handler [pf] .data = NULL; 395 br_write_unlock_bh (BR_NETPROTO_LOCK); 396 return 0; 397} 398 399 / * 400 * Any Packet That Leaves Via this function Must Come Back 401 * THROUGH NF_RENJECT (). 402 * / nf_queue first checks if there is a queue processing function, if not, the group cannot be processed, only discard, then return. The packet assigned by SKB is then assigned and an additional Netfilter information head is attached. If there is no space, print the error message. After the two works are completed, the process of calling the queue processing this group. If an error occurs during the process, the packet is discarded and the assigned NetFilter information header space is returned. 403 static void nf_queue (struct sk_buff * skb, 404 struct list_head * elem, 405 int pf, unsigned int hook, 406 struct net_device * indev, 407 struct net_device * outdev, 408 int (* okfn) (struct sk_buff *)) 409 { 410 int status; 411 struct nf_info * info; 412 413 if (! Queue_handler [pf] .outfn) {414 kfree_skb (SKB); 415 return; 416} 417 418 info = kmalloc (Sizeof (* info), GFP_ATOTIN; 419 IF (! info) {420 IF (Net_RATELIMIT ()) 421 Printk (kern_err "oom queueing packet% p / n", 422 SKB); 423 kfree_skb (SKB); 424 return; 425} 426 427 * info = (Struct NF_INFO ) {428 (struct nf_hook_ops *) ELEM, PF, HOOK, INDEV, OUTDEV, OKFN}; 429 430 / * Bump dev rebs so they don't vanish while packet is out * / 431 if (indev) dev_hold (indev); 432 if (Outdev) dev_hold (Outdev); 433 434 Status = queue_handler [pf] .outfn (SKB, INFO, Queue_Handler [Pf] .data); 435 IF (status <0) {436 / * James m Doesn't Say [CENSORED] ENOUGH. * / 437 if (indev) DEV_PUT (INDEV); 438 if (Outdev) DEV_PUT (OUTDEV); 439 KFree (INFO); 440 kfree_skb (SKB); 441 Return; 442} 443} 444 The following function is a key function for Netfilter's kernel because each hook handles the packets, is done by calling this function.
445 int nf_hook_slow (int pf, unsigned int hook, struct sk_buff * skb, 446 struct net_device * indev, 447 struct net_device * outdev, 448 int (* okfn) (struct sk_buff *)) 449 {450 struct list_head * elem; 451 unsigned INT Verdict; 452 int RET = 0; 453 454 / * We May Already Have this, but read-locks nest anyway * / read lock, such as comment, there is a nested to the lock. 455 br_read_lock_bh (BR_NETPROTO_LOCK); 456 debug information 457 #ifdef CONFIG_NETFILTER_DEBUG 458 if (skb-> nf_debug & (1 << hook)) {459 printk ( "nf_hook: hook% i already set./n", hook); 460 nf_dump_skb (PF, SKB); 461} 462 SKB-> NF_DEBUG | = (1 << Hook); 463 #ENDIF 464 Select the Response Hook Lin table based on a given protocol group parameter and hook value. 465 elem = & nf_hooks [pf] [hook]; traversal chain table, and processed to the setup group, return value to determine the fate of the group. 466 Verdict = NF_ITERATE (& NF_HOOKS [PF] [HOOK], & SKB, HOOK, INDEV, 467 OUTDEV, & ELEM, OKFN; Packet queuing 468 if (verdict == nf_queue) {469 nfdebug ("nf_hook: verdict = queue. / N "); 470 nf_queue (SKB, ELEM, PF, HOOK, INDEV, OUTDEV, OKFN); 471} 472 473 Switch (Verdict) {If the packet can be accepted, the subsequent function is processed. As for this, please refer to the post of the relationship between Netfilter's hook. 474 reset: 475 RET = OKFN (SKB); 476 Break; 477 If the packet is unacceptable, discard the packet 478 case nf_drop: 479 kfree_skb (SKB); 480 RET = -eperm; 481 break; 482} 483 Release lock 484 br_read_unlock_bh (Br_netproto_lock); 485 Return Ret; 486} 487 Treatment Queuing packet, each of the packets processed by NF_QUEUE, eventually processed by NF_REINJECT.
488 void nf_reinject (struct sk_buff * skb, struct nf_info * info, 489 unsigned int verdict) 490 {491 struct list_head * elem = & info-> elem-> list; 492 struct list_head * i; 493 494 / * We do not have BR_NETPROTO_LOCK HERE * / Read Lock 495 Br_READ_LOCK_BH (BR_NETPROTO_LOCK) Check that the module that passes the group to the user space exists 496 for (i = nf_hook [info-> pf] [info-> hook] .next; i! = Elem; i = I-> Next) {497 if (i == & nf_hooks [info-> pf] [info-> hook]) {498 / * The module which time it to userspace is gone. * / If there is no existence, discard Group. 499 NFDebug ("% s: module disappeared, 500 __function__); 501 verdict = nf_drop; 502 Break; 503} 504} 505 If a given parameter verdict says that user space can receive a packet, then we continue to process .