FreeBSD/sys/netpfil/ipfw/ip_fw_sockopt.c
/*
 * Checks is opcode is referencing table of appropriate type.
 * Adds reference count for found table if true.
 * Rewrites user-supplied opcode values with kernel ones.
 *
 * Returns 0 on success and appropriate error code otherwise.
 */
Checks is opcode is referencing table of appropriate type.
Adds reference count for found table if true.
Rewrites user-supplied opcode values with kernel ones.

Returns 0 on success and appropriate error code otherwise.
Checks is opcode is referencing table of appropriate type . Adds reference count for found table if true . Rewrites user - supplied opcode values with kernel ones . Returns 0 on success and appropriate error code otherwise .
static int
rewrite_rule_uidx(struct ip_fw_chain *chain, struct rule_check_info *ci)
{
	int error;
	ipfw_insn *cmd;
	uint8_t type;
	struct obj_idx *p, *pidx_first, *pidx_last;
	struct tid_info ti;
	if (ci->object_opcodes <= (sizeof(ci->obuf)/sizeof(ci->obuf[0]))) {
		pidx_first = ci->obuf;
	} else
		pidx_first = malloc(
		    ci->object_opcodes * sizeof(struct obj_idx),
		    M_IPFW, M_WAITOK | M_ZERO);
	error = 0;
	type = 0;
	memset(&ti, 0, sizeof(ti));
	ti.set = ci->krule->set;
	if (ci->ctlv != NULL) {
		ti.tlvs = (void *)(ci->ctlv + 1);
		ti.tlen = ci->ctlv->head.length - sizeof(ipfw_obj_ctlv);
	}
	error = ref_rule_objects(chain, ci->krule, ci, pidx_first, &ti);
	if (error != 0)
		goto free;
	p = pidx_first;
	pidx_last = pidx_first + ci->object_opcodes;
	for (p = pidx_first; p < pidx_last; p++) {
		cmd = ci->krule->cmd + p->off;
		update_opcode_kidx(cmd, p->kidx);
	}
free:
	if (pidx_first != ci->obuf)
		free(pidx_first, M_IPFW);
	return (error);
}
static int rewrite_rule_uidx ( struct ip_fw_chain * chain , struct rule_check_info * ci ) { int error ; ipfw_insn * cmd ; uint8_t type ; struct obj_idx * p , * pidx_first , * pidx_last ; struct tid_info ti ; if ( ci -> object_opcodes <= ( sizeof ( ci -> obuf ) / sizeof ( ci -> obuf [ 0 ] ) ) ) { pidx_first = ci -> obuf ; } else pidx_first = malloc ( ci -> object_opcodes * sizeof ( struct obj_idx ) , M_IPFW , M_WAITOK | M_ZERO ) ; error = 0 ; type = 0 ; memset ( & ti , 0 , sizeof ( ti ) ) ; ti . set = ci -> krule -> set ; if ( ci -> ctlv != NULL ) { ti . tlvs = ( void * ) ( ci -> ctlv + 1 ) ; ti . tlen = ci -> ctlv -> head . length - sizeof ( ipfw_obj_ctlv ) ; } error = ref_rule_objects ( chain , ci -> krule , ci , pidx_first , & ti ) ; if ( error != 0 ) goto free ; p = pidx_first ; pidx_last = pidx_first + ci -> object_opcodes ; for ( p = pidx_first ; p < pidx_last ; p ++ ) { cmd = ci -> krule -> cmd + p -> off ; update_opcode_kidx ( cmd , p -> kidx ) ; } free : if ( pidx_first != ci -> obuf ) free ( pidx_first , M_IPFW ) ; return ( error ) ; }
Checks is opcode is referencing table of appropriate type.
Checks is opcode is referencing table of appropriate type .
/*
	 * Prepare an array for storing opcode indices.
	 * Use stack allocation by default.
	 */ /* Stack */ /* Use set rule is assigned to. */ /* Reference all used tables and other objects */ /*
	 * Note that ref_rule_objects() might have updated ci->object_opcodes
	 * to reflect actual number of object opcodes.
	 */ /* Perform rewrite of remaining opcodes */