VHPI standard Callback Spec ~~~~~~~~~~~~~~~~~~~~~~~~~~~ I. Public functions, methods and properties: ============================================ I.1 Registration of callbacks ----------------------------- (vhpiHandleT) vhpi_register_cb (vhpiCbkDataT *cbkData_p, int flags); A callback data structure is allocated by the user and passed to the register callback function. The function will return a callback handle if the callback was successfully created and if the flag argument was set to vhpiReturnCb otherwise it will return NULL. if the flag is set to vhpiDisable, the callback is installed but is initially disabled. The callback data structure is described in section II.2. I.2 Removal of callbacks ----------------------- (int) vhpi_remove_cb(vhpiHandleT cb_hdl); Given a callback handle, this function will remove the callback. The callback will not occur anymore. The function return 1 on success and 0 on failure. It will also free the callback handle, if one was created. I.3 Disabling and enabling callbacks ----------------------------------- (int) vhpi_disable_cb(vhpiHandleT cb_hdl); (int) vhpi_enable_cb(vhpiHandleT, cb_hdl); vhpi_disable_cb disables the callback from happening until it is enabled again by vhpi_enable_cb. vhpi_enable_cb reinstalls the callback. The functions return 1 on success and 0 on failure. A warning should be issued if the callback has matured and is not a repetitive callback. We extend the functions to work on any callback reason. It makes generally sense to disable repetitive callback of reasons vhpiCbkValueChange, vhpiCbkStmt, vhpiCbkTransaction, vhpiCbkError. I.4 Callback information ----------------------- (int) vhpi_get_cb_info (vhpiHandleT cbhdl, vhpiCbkDataT *cb_data_p); Given a callback handle, fill up the vhpiCbkDataT structure that has been allocated by the user with original information regarding the callback. The function returns 1 on success and 0 and failure. I.5 Callback methods ------------------- The callback UML class diagram illustrates the methods and properties that are available for callbacks. Iteration on vhpiCallback from the tool (NULL) will return all callback handles (including the disabled, freed but not removed and matured one. The reason to return even the disable or freed callbacks is that someone needs to get all callbacks existing currently. Iteration from an object declaration will return all value change callbacks registered for the object pointer by the handle in the obj field of the vhpiCnkDataT structure (including the disabled and freed ones). Iteration from a statement handle will return all vhpiCbkStmt callbacks registered for the statement pointed by the handle in the obj field of the vhpiCbkDataT structure (even the disabled and freed ones). Iteration from a time queue handle will return all time related callbacks that have been registered for this time queue (i.e this simulation time slice). Iteration from an indexedName or selected name will return value change callbacks that have been registered for the object indicated by the handle in the obj field. Iterating from a driver handle will return all registered callbacks for reason vhpiCbkTransaction for this driver. I.6 Callback properties ---------------------- vhpiReasonP: gets the callback reason vhpiStateP: is the callback disabled, matured, or active? mature: the callback has happened. Repetitive callbacks never mature. II Callback description ======================== II.1 Callback reasons ---------------------- /************************* Simulation objects related ************************/ #define vhpiCbkValueChange 1 /* for variable, signal, etc... value change, the object handle should be set to designate the variable, signal etc... */ #define vhpiCbkIndexValueChange /* for composite object handles only: a value change callback will happen for each array element or field record element that changed value */ #define vhpiCbkStmt 2 /* before a sequential statemnt executes or after a concurrent statement completed its execution */ #define vhpiCbkForce 3 /* after a force occurred on a variable or signal */ #define vhpiCbkRelease 4 /* after a release happened on a forced variable or signal */ #define vhpiCbkTransaction /* before a driver transaction matures */ #define vhpiCbkRetFuncCall /* Before a given function call returns from execution */ #define vhpiCbkEndOfSubpCall /* The subprogram call has completed execution */ /****************************** Time related ******************************/ #define vhpiCbkNextTimeStep 8 /* at the beginning of the next time slice The simulation time has just advanced, and no signal values have been updated yet. Immediate signal value updates with event or zero delay event scheduling that are done by this sort of callback take place in the first cycle of the time step. #define vhpiCbkAfterDelay 9 /* Callback happens at the current simulation plus delay that is indicated by the time structure even if there is no event to be scheduled at this time; the callback occurs at the beginning of the simulation time, before values gets updated and events execute */ #define vhpiCbkBeginNextCycle /* at the beginning of the next simulation delta cycle */ #define vhpiCbkEndPropagation /* callback happens after all update and propagation of signals has been done, just before process execute */ #define vhpiCbkEndProcesses /* Callback occurs when all non-postponed processes have run, just before the postponed processes execute */ #define vhpiCbkEndTimeStep /* callback happens at the end of the time slice, time has not advanced yet */ Note: if, when registering the callback, the phase (endPropagation or processes, or nextTimeStep, beginNextCycle, endTimeStep has passed, the callback in put on the next closest simulation phase. /***************************** Action related *****************************/ #define vhpiCbkElaboration 10 /* for the elaboration of each foreign model and at the end of elaboration */ #define vhpiCbkStartOfSimulation 11 /* when simulation starts, after simulation initialization */ #define vhpiCbkEndOfSimulation 12 #define vhpiCbkQuiescense /* when no more event in the time wheel */ #define vhpiCbkError 13 /* on a simulation assertion or VHPI detected error */ #define vhpiCbkPLIError /* a VHPI error occured */ #define vhpiCbkStartOfSave 15 #define vhpiCbkEndOfSave 16 #define vhpiCbkStartOfRestart 17 #define vhpiCbkEndOfRestart 18 #define vhpiCbkStartOfReset 19 #define vhpiCbkEndOfReset 20 #define vhpiCbkEnterInteractive 21 #define vhpiCbkExitInteractive 22 #define vhpiCbkSigInterrupt /* when a special OS signal interruption occurs */ II.2. Callback structure --------------------- /* callback user data structure */ typedef struct vhpiCbkDataS { int reason; /* callback reason */ int (*cb_rtn)(); /* call routine */ vhpiHandleT obj; /* trigger object */ vhpiTimeT *time; /* callback time */ vhpiValueT *value; /* trigger object value */ int index; /* index of the element of the object that changed */ void *user_data; /* pointer to user data to be passed to the callback function */ } vhpiCbkDataT; II.2 Simulation object callbacks -------------------------------- For all callbacks, the reason and the cb_rtn functions must be set. Additional fields may be set depending on the reason. If the time and value fields are not null, they must have a valid format. The callback function designated by cb_ret, will take only one argument which is a pointer to the vhpi_cb_data structure. vhpiCbkValueChange: the obj should be set to the object of interest which can be of the following types: vhpiSigDecl, vhpiVarDecl, vhpiSharedVarDecl, vhpiPortDecl, vhpiSigParamDecl, vhpiVarParamDecl, vhpiIndexedName, vhpiSelectedName and the signal attributes delayed, stable, quiet and transaction. If the user wants the time of when the callback happens, he must set the time field to point to an allocated time structure, if he wants the resulting value, he must pass a pointer to an allocated value structure. Only one callback will occur for the whole object even if more than one scalar element changes value in the same delta cycle. vhpiCbkTransaction: the obj must be set to a driver handle. The callback will happen everytime a transaction matures for that driver. The value and time fields if not null will be set to the value and time of the transaction. vhpiCbkForce, vhpiCbkRelease: the obj field must be set to a handle of the following types: vhpiSigDecl, vhpiVarDecl, vhpiSharedVarDecl, vhpiPortDecl, vhpiSigParamDecl, vhpiVarParamDecl, vhpiAliasObjDecl, vhpiIndexedName, vhpiSelectedName. The callback will fire after a force or release has occured on the designated object. The value and time fields if not NULL indicate the value after the force or release and the time of the force or release action. If the obj field is null, then the callback should happen everytime a force or a release occurs, the obj field will contain the handle of the object that caused the callback. vhpiCbkStmt: the object field must be set to a handle to a concurrent or sequential statement The callback will fire before the statement executes. If the time field is not null it will be set to the time of the callback. II.3 Time related callbacks: ---------------------------- These are all one time callbacks. There is no repetitive time callback. No fields of the vhpi_cb_data structure are filled up by the tool when the callback occurs. vhpiCbkNextTimeStep, no additional field need to be set. The callback will occur at the beginning of the next time slice before any signal value gets updated. vhpiCbkAfterDelay, the time field should indicate the requested delay. Callback happens at the time computed with the delay. before execution of the events of in this specified time queue. Callback happens even if no transactions are present. vhpiCbkBeginNextCycle, no additional field need to be set. Callback happens at the beginning of the next simulation cycle. vhpiCbkEndProcesses: no additional field need to be set. Callback happens after all non-postponed processes have run just before postponed processes executes if there is any. vhpiCbkEndPropagation: after the update and propagation phases, all signal have their effective value for this cycle vhpiBeginPostponedProcess: before postponed processes execute, this was the last delta cycle. vhpiCbkEndTimeStep: af the end of the time slice, just before time advances THis is equivalent to vhpiCbkNextTimeStep excet that the time has not advanced. no need for this one... II.4 Action related callbacks: ------------------------------ Except for vhpiCbkEndOfElaboration, vhpiCbkStartOfSimulation and vhpiCbkEndOfSimulation, all other callbacks are repetitive callbacks that can be disabled and enabled. vhpi reset/restart and save callbacks are defined in another spec. vhpiCbkEndOfElaboration, callback happens after elaboration vhpiCbkStartOfSimulation, callback occurs when simulation starts, after simulation initialization vhpiCbkEndOfSimulation, callback happens when the simulation is going to exit vhpiCbkQuiescence, callback happens when the simulation has reached a quiet state. no more events are scheduled. vhpiCbkError, callback happens when an error occurs, the error is either a tool or interface error.. The function vhpi_chk_error can be called during the callback function to retrieve error information. The error info data structure if provided will be filled up with the appropriate (tool or interface) error information. vhpiCbkPLIError : callback when a VHPI error ocurs vhpiCbkStartOfSave, callback happens at the beginning of a save vhpiCbkEndOfSave, callback happens at the end of a save vhpiCbkStartOfRestart, callback occurs at the beginning of a restart vhpiCbkEndOfRestart, callback occurs at the end of restart vhpiCbkStartOfReset, callback occurs at the beginning of a reset vhpiCbkEndOfReset, callback happens at the end of a reset vhpiCbkEnterInteractive, callback happens when the control is given to the user to interact with the tool (breakpoint from the gui, commandline etc...) This callback is useful when the user wants some C code to be executed when the simulator stops (is interrupted by the user or a script) and wants to do either debug or read values from files for ex, all of this is written in C and performed by the function pointer provided in the callback data structure. vhpiCbkExitInteractive, callback occurs when the control is returned to the simulator vhpiCbkSigInterrupt: callback happens on a specified OS signal. The obj field of the vhpi_cb_data structure is the signal identifier number could one of (not limited to SIGINT, SIGKILL, SIGCHLD, SIGUSR1 SIGUSR2...) (see system file signal.h and man pages on sigaction) The user gets called back when it is safe to be called. III Callback execution ====================== When a callback happens, the cb_rtn function indicated by the vhpiCbkDataS structure is called with one parameter a vhpiCbkData structure pointer. The vhpi_cb_data structure is not a pointer to the same structure that was passed to vhpi_register_cb but is reproducing the vhpiCbkData_structure fields user settings. Some additional fields may have been filled up before passing the cb_data pointer to the callback function to provide some information; potentially modifed fields include: obj, index, time, value All VHPI public functions can be called during the execution of a cb_rtn function. The cb_rtn function returns a int *. IV Issues & questions: ----------------------- ii) Do we need this type of callback? callback at the end of the time slice if one of a list of signals or variables changed value: Why: one callback registration instead of one per each object. for performance reason: only get one callback at the end of the time slice. This needs more thinking because at the end of a time slice, we may have to go and get the values of all objects... iii) vhpiCbkEndOfElaboration: This truly does not contain the first initialization cycle of the simulation when all concurrent processes run once to reach their first state. chkStartofSimulation will be a callback after this first init sim cycle has finished. vhpiCbkEndOfElaboration would be used in the elaborator. vhpiCbkStartOfSimulation would be used in the simulator. vhpiCbkEndOfElaboration could be used for invoking VHPI applications. iv) since we have cbValueChange we don't need a cbEvent? Does the value change callback happens during update and propagation phases or just before the process executes? I think it occurs just before the processes execute. v) vhpiCbkError, vhpiCbkPLIError: Would it be possible to filter some levels of error, only get callback on assertions errors and not NOTE? I am inclined to say that the callback function can filter it otherwise we end up with a slew of callback reasons. vi) Is the callback before a concurrent statement execution realistic and useful? Putting a callback on the first sequential statement of a behavioral concurrent statement may be sufficient. On the other end, a callback that happens at the end of the execution of a concurrent statement just before the control returns to the kernel would be more helpful. What does this mean for structural concurrent statements such as component instances, generate instances etc... No need to apply this for structural instances. vii) In a mixed language design,should equivalent VHPI callbacks such as ckbForce or vhpiCbkRelease be extended to the Verilog parts of the design? For example a callback for reason vhpiCbkForce will occur for any force done on any object independently it is a Verilog or VHDL object. Since some callbacks are equivalent in a mixed language design where VPI and VHPI applications are present it is not necessary to place 2 equivalent callbacks such as vhpiCbkStartofSimulation for VPI and one for VHPI. No I think that we need both applications to register the two callbacks. vhpiCbkForce will only apply to Verilog forces, and vhpiCbkkForce will only apply to VHDL forces. viii) Do we need these callbacks: vhpiCbkStartOfElaboration NO vhpiCbkStartOfInitialization this marks when the first simulation initialization cycle is about to start. No, if we see the need for them, we will add them V Callback priority classification ================================== The priority ranges from 0 (critical to 1 important, 2 interesting) Mandatory callbacks: priority Optional Callbacks priority vhpiCbkValueChange 0 vhpiCbkStmt 2 vhpiCbkForce 2 vhpiCbkRelease 2 vhpiCbkTransaction 2 vhpiCbkRetFuncCall vhpiCbkNextTimeStep 1 vhpiCbkAfterDelay 0 vhpiCbkBeginNextCycle 2 vhpiCbkEndPropagation vhpiCbkEndProcesses 1 vhpiCbkEndTimeStep 1 vhpiCbkEndOfInitialization vhpiCbkStartOfSimulation 0 vhpiCbkEndOfSimulation 0 vhpiCbkQuiescense 2 vhpiCbkError 2 vhpiCbkPLIError vhpiCbkStartOfSave 2 vhpiCbkEndOfSave 2 vhpiCbkStartOfRestart 2 vhpiCbkEndOfRestart 2 vhpiCbkStartOfReset 2 vhpiCbkEndOfReset 2 vhpiCbkEnterInteractive vhpiCbkExitInteractive vhpiCbkUnresolvedForeignf vhpiCbkSigInterrupt Total number of mandatory callbacks: 20 (6 of which are reset/save/restart vhpiCbk)