📄 v_vxdemo.c
字号:
static int lastSerialNum; static OID * last_incoming; int reqVar = -1; if ((lastSerialNum != serialNum) || (pTaskEntry == NULL) || (CmpOIDInst(incoming, last_incoming, object->oid.length) != 0)) { /* * instLength represents the length of the (incoming) requested OID * beyond the Object Identifier specified in the MIB tree. This value * is used to validate the request on an EXACT or NEXT search. Ex. * The MIB variable fakeMibVar = OID 1.3.6.1.4.1.731.1.1.2 and is * specified this way in the object variable. The incoming would * have fakeMibVar.0 = OID 1.3.6.1.4.1.731.1.1.2.0, the length would * be 1 and the last value 0. This information is used to valiate the * EXACT search. In the case of a NEXT search the length must be 0 * for leaf variables. For table entries with an integer index the * incoming OID would be 1.3.6.1.4.1.731.1.1.2.INDEX and the length * would represent the index. */ instLength = incoming->length - object->oid.length; /* * The task ID is set to zero in case the INDEX is not specified and the * first table entry is requested. */ taskId = 0; switch (searchType) { case EXACT: if (instLength == 1) { reqVar = object->nominator; /* Field in the table req */ taskId = (long) incoming->oid_ptr [object->oid.length]; } break; case NEXT: reqVar = object->nominator; /* Field in the table req */ /* * If the taskId was not specify, use task ID of 0 to access * the first entry, otherwise pick the taskId from the * requested OID. */ taskId = (instLength < 1) ? 0 : (unsigned long) incoming->oid_ptr [object->oid.length]; break; default: DPRINTF((0, "snmpd: Internal error. (invalid search type in \ taskEntry_get -- %d)\n", searchType)); } /* Retrieve the data from the kernel-specific routine. */ if (reqVar == -1 || (pTaskEntry = k_taskEntry_get (serialNum, contextInfo, reqVar, searchType, taskId)) == NULL) { return ((VarBind *) NULL); /* Entry not Found or End of the Table */ } /* * Return to SNMP NM the INDEX of the entry whose OID was requested * this INDEX will be used to request more OIDs of the same entry * entry or to request the NEXT entry in the table. */ inst.length = 1; inst.oid_ptr = &oidbuff; inst.oid_ptr [0] = pTaskEntry->taskId; /* Get new catche information */ lastSerialNum = serialNum; if (last_incoming != NULL) FreeOID(last_incoming); last_incoming = CloneOID(incoming); } else { reqVar = object->nominator; /* Field in the table req */ } switch (reqVar) { case I_taskName: dp = (void *) MakeOctetString (pTaskEntry->taskName->octet_ptr, pTaskEntry->taskName->length); break; case I_taskMain: dp = (void *) MakeOctetString (pTaskEntry->taskMain->octet_ptr, pTaskEntry->taskMain->length); break; default: /* * Any other variable requested can be access using the S_OFFSET * macro, which computes the offset of the variable in the * structure and returns a pointer to the variable. */ dp = S_OFFSET(pTaskEntry, reqVar); } /* * Construct the response for the SNMP agent. The structure returned * will be strung onto the response PDU. The inst parameter contains the * index in the table for the requested variable. */ return (MakeVarBind (object, &inst, dp)); }/********************************************************************************* taskEntry_free - Free the taskEntry data structure.** This routine is invoked indirectly by the SNMP agent to free the taskEntry* structure that was allocated during the call to test, and after the call to* set, or after the test fails.** RETURNS: N/A** SEE ALSO:*/void taskEntry_free ( taskEntry_t * ptaskEntry ) { if (ptaskEntry != NULL) { if (ptaskEntry->taskName != NULL) FreeOctetString (ptaskEntry->taskName); if (ptaskEntry->taskMain != NULL) FreeOctetString (ptaskEntry->taskMain); free ((char *) ptaskEntry); } }/********************************************************************************* taskEntry_cleanup - Free all the resources allocated in taskEntry_test.** This routine is invoked by the SNMP agent after the set operation has taken* placed or if the test routine failed.** RETURNS: NO_ERROR always successful.** SEE ALSO:*/LOCAL int taskEntry_cleanup ( doList_t *trash ) { taskEntry_free (trash->data); taskEntry_free (trash->undodata); return NO_ERROR; }/********************************************************************************* taskEntry_undo - provided for future use** RETURNS: ERROR** SEE ALSO:*/LOCAL int taskEntry_undo ( ) { return UNDO_FAILED_ERROR; }/********************************************************************************* taskEntry_test - Validate new values for the MIB variables.** This routine ensures that the value to which a MIB variable is to be set is* in accordance to its MIB definition in the file vxdemo.my. After all the* variables required to update the an entry or variable is collected, the state* of the doList structure is set to ADD_MODIFY or DELETE, based on the operaion* requested.** RETURNS: NO_ERROR for successful validation, otherwise an error is returned.** SEE ALSO:*/int taskEntry_test ( OID * incoming, /* Ptr to the OID received in the SNMP PDU */ ObjectInfo * object, /* Ptr to MIB var in the SNMP MIB tree */ ObjectSyntax * value, /* Ptr the value to set the MIB variable */ doList_t * doHead, /* Ptr to the list of SNMP outstanding reqs */ doList_t * doCur, /* Ptr to free doList element */ ContextInfo * contextInfo /* Reserved for future used */ ) { long taskId; /* Task ID is used for table index */ doList_t * dp; taskEntry_t * ptaskEntry; int instLength; /* * instLength represents the length of the (incoming) requested OID * beyond the Object Identifier specified in the MIB tree. This value * is used to validate the request on an EXACT or NEXT search. Ex. * The MIB variable fakeMibVar = OID 1.3.6.1.4.1.731.1.1.2 and is * specified this way in the object variable. The incoming would * have fakeMibVar.0 = OID 1.3.6.1.4.1.731.1.1.2.0, the length would * be 1 and the last value 0. This information is used to valiate the * EXACT search. In the case of a NEXT search the length must be 0 * for leaf variables. For table entries with an integer index the * incoming OID would be 1.3.6.1.4.1.731.1.1.2.INDEX and the length * would represent the index. In the case of a set operation the variable * needs to be specified exactly and therefore the length must be 1. */ instLength = incoming->length - object->oid.length; if (instLength != 1) return (NO_ACCESS_ERROR); /* Get the index of the entry that is to be modified */ taskId = (long) incoming->oid_ptr [incoming->length - 1]; /* * There is a single list of SNMP outstanding requests. The list * is shared by all "v_" routines in the agent. Each time a variable * is SET the list must be search for the corresponding data structure. * if the structure does not exits it must be allocated. This space * is freed by the "*free" routine. */ for (dp = doHead; dp != NULL; dp = dp->next) { if ((dp->setMethod == taskEntry_set) && ((void *) (dp->data) != (void *) NULL) && (((taskEntry_t *) (dp->data))->taskId == taskId)) { break; /* Structure found */ } } if (dp == NULL) { dp = doCur; if ((dp->data = (void *) calloc (1, sizeof(taskEntry_t))) == NULL) { DPRINTF((0, "snmpd: Can't alloc memory in taskEntry_test\n")); return (GEN_ERROR); } dp->setMethod = taskEntry_set; dp->cleanupMethod = taskEntry_cleanup; dp->undoMethod = taskEntry_undo; dp->state = UNKNOWN; SET_VALID(I_taskId, ((taskEntry_t *) (dp->data))->valid); ((taskEntry_t *) (dp->data))->taskId = taskId; } /* * Zero is not a valid task ID in vxWorks and is used in this * implementation for the creation of new tasks. If the ID is * not zero then the ID is validated. */ if ((taskId != 0) && (k_taskEntry_get (-1, contextInfo, object->nominator, EXACT, taskId) == NULL)) return (NO_ACCESS_ERROR); /* taskId does not exist */ /* * Add the SET request to the do-list element. Test the validity of the * value requested to be set. */ ptaskEntry = (taskEntry_t *) dp->data; switch (object->nominator) { case I_taskId: /* The task ID of an executing task can't be changed. */ if ((taskId != 0) && (taskId != value->sl_value)) return (NOT_WRITABLE_ERROR); /* ELSE: Not used for anything else in this code */ break; case I_taskName: /* The name of the task can be only changed at creation time */ if (taskId != 0) return (NOT_WRITABLE_ERROR); ptaskEntry->taskName = MakeOctetString (value->os_value->octet_ptr, value->os_value->length); SET_VALID(I_taskName, ptaskEntry->valid); break; case I_taskPriority: /* Task Priority must be in the range 1 - 255 */ if (value->sl_value < 0 || value->sl_value > 255) return (WRONG_VALUE_ERROR); ptaskEntry->taskPriority = value->sl_value; SET_VALID(I_taskPriority, ptaskEntry->valid); break; case I_taskStatus: /* The status of a task can only if the task has been created */ if (taskId == 0) return (NOT_WRITABLE_ERROR); if (value->sl_value != D_taskStatus_task_ready && value->sl_value != D_taskStatus_task_suspended && value->sl_value != D_taskStatus_task_delay && value->sl_value != D_taskStatus_task_deleted) return (WRONG_LENGTH_ERROR); ptaskEntry->taskStatus = value->sl_value; SET_VALID(I_taskStatus, ptaskEntry->valid); break; case I_taskOptions: /* * If a task is being created any options can be changed. Otherwise * the only option that can be changed is VX_UNBREAKABLE. */ if (taskId == 0) { if ((value->sl_value & (VX_UNBREAKABLE | VX_DEALLOC_STACK | VX_FP_TASK | VX_PRIVATE_ENV | VX_NO_STACK_FILL | VX_SUPERVISOR_MODE | VX_STDIO)) == 0 ) return (WRONG_VALUE_ERROR); } else { /* Task is running and only VX_UNBREAKABLE can be changed */ if (value->sl_value != VX_UNBREAKABLE) return (WRONG_VALUE_ERROR); } ptaskEntry->taskOptions = value->sl_value; SET_VALID(I_taskOptions, ptaskEntry->valid); break; case I_taskMain: /* Task entry point routine, can be only set at creation time */ if (taskId != 0) return (NOT_WRITABLE_ERROR); ptaskEntry->taskMain = MakeOctetString (value->os_value->octet_ptr, value->os_value->length); SET_VALID(I_taskMain, ptaskEntry->valid); break; case I_taskStackSize: /* The stack size can only set at the time the task is created */ if (taskId != 0) return (NOT_WRITABLE_ERROR); ptaskEntry->taskStackSize = value->ul_value; SET_VALID(I_taskStackSize, ptaskEntry->valid); break; default: DPRINTF((0, "snmpd: Internal error (invalid nominator \ in atEntry_test)\n")); return (GEN_ERROR); } /* * Existing table entries that are being modified are moved to the * ADD_MODIFY state. If a task is being created all the required * parameters must be set before the request is moved to the ADD_MODIFY * state. */ if (taskId != 0) { if (ptaskEntry->taskStatus == D_taskStatus_task_deleted) dp->state = DELETE; else dp->state = ADD_MODIFY; } else if (VALID(I_taskName, ptaskEntry->valid) && VALID(I_taskMain, ptaskEntry->valid) && VALID(I_taskPriority, ptaskEntry->valid) && VALID(I_taskStackSize, ptaskEntry->valid) && VALID(I_taskOptions, ptaskEntry->valid)) dp->state = ADD_MODIFY; return (NO_ERROR); }/********************************************************************************* taskEntry_set - Invokes k_ logic to set the task entry.*** This set routine assumes that the variables to be set are correct. This* assumption is safe because the test routine has already validated the* variable(s) and set the state of the operation.** RETURNS: Success or Error to the SNMP agent.
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -