Linux内核分析 - 网络[四]:路由表
如 何fib_node还不存在,则会创建它,这里的kmem_cache_zalloc()其实就是内存分配 new_f = kmem_cache_zalloc (fn_hash_kmem, GFP_KERNEL); if (new_f == NULL) goto out; INIT_HLIST_NODE(&new_f- >fn_hash); INIT_LIST_HEAD(&new_f->fn_alias); new_f->fn_key = key; f = new_f; 路由表最后一层是fib_info,具体的路由信息都存储在此,它由 fib_create_info()创建。 首先为fib_info分配空间,由于fib_info的最后一个属性是struct fib_nh fib_nh[0],因此 大小是fib_info + nhs * fib_nh,这里的fib_nh代表了下一跳(next hop)的信息,nhs代表了下一跳的数目,一般情况下nhs=1 ,除非配置了支持多路径。 fi = kzalloc(sizeof(*fi)+nhs*sizeof(struct fib_nh), GFP_KERNEL); 设置fi的相 关属性 fi->fib_net = hold_net(net); fi->fib_protocol = cfg->fc_protocol; fi- >fib_flags = cfg->fc_flags; fi->fib_priority = cfg->fc_priority; fi->fib_prefsrc = cfg->fc_prefsrc; fi->fib_nhs = nhs; 使fi后面所有的nh->nh_parent指向fi,设置后如图所示 change_nexthops(fi) { nexthop_nh->nh_parent = fi; } endfor_nexthops(fi) 设置fib_nh的属性, 这里仅展示了单一路径的情况: struct fib_nh *nh = fi->fib_nh; nh->nh_oif = cfg- >fc_oif; nh->nh_gw = cfg->fc_gw; nh->nh_flags = cfg->fc_flags; 然后,再根据cfg ->fc_scope值来设置nh的其余属性。如果scope是RT_SCOPE_HOST,则设置下一跳scope为RT_SCOPE_NOWHERE if (cfg- >fc_scope == RT_SCOPE_HOST) { struct fib_nh *nh = fi->fib_nh; nh->nh_scope = RT_SCOPE_NOWHERE; nh->nh_dev = dev_get_by_index(net, fi->fib_nh->nh_oif); } 如果scope 是RT_SCOPE_LINK或RT_SCOPE_UNIVERSE,则设置下跳 change_nexthops(fi) { if ((err = fib_check_nh(cfg, fi, nexthop_nh)) != 0) goto failure; } endfor_nexthops(fi) 最后,将fi链入链表中,这里要注意的 是所有的fib_info(只要创建了的)都会加入fib_info_hash中,如果路由项使用了优先地址属性,还会加入fib_info_laddrhash 中。 hlist_add_head(&fi->fib_hash, &fib_info_hash[fib_info_hashfn(fi)]); if (fi- >fib_prefsrc) { struct hlist_head *head; head = &fib_info_laddrhash[fib_laddr_hashfn(fi- >fib_prefsrc)]; hlist_add_head(&fi->fib_lhash, head); } (编辑:应用网_丽江站长网) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |