Difference between revisions of "Event Notification (Hot-Link)"

From MidasWiki
Jump to navigation Jump to search
(Created page with "==== Links ==== <div style="column-count:3;-moz-column-count:3;-webkit-column-count:3"> * Frontend user code * Equipment List Parameters </div> ==Introduction== MIDA...")
 
 
(6 intermediate revisions by 2 users not shown)
Line 1: Line 1:
==== Links ====
+
<div style="column-count:4;-moz-column-count:4;-webkit-column-count:4">
 +
* [[Midas_documentation|Midas Documentation]]
 +
* [[Feature_listing|Feature Listing]]
 +
* [[Application_listing|Application Listing]]
 +
* [[Online_Database|Online Database]]
 +
</div>
 +
 
 +
<br>
 +
 
 +
= Links =
 
<div style="column-count:3;-moz-column-count:3;-webkit-column-count:3">
 
<div style="column-count:3;-moz-column-count:3;-webkit-column-count:3">
 +
* [[Hotlink note]]
 
* [[Frontend user code]]  
 
* [[Frontend user code]]  
 
* [[Equipment List Parameters]]
 
* [[Equipment List Parameters]]
 
</div>
 
</div>
  
==Introduction==
+
<div id="hotlink"></div>
 +
 
 +
=Introduction=
 
MIDAS implements event notification through "'''hot-links'''". Once a hot-link is established to a key in the ODB, immediately that key is accessed, a call-back routine associated with the hot-link is called to perform whatever action has been programmed. The MIDAS system uses hot-links to update keys in the ODB for communication between system clients  (e.g. [[History System]]).
 
MIDAS implements event notification through "'''hot-links'''". Once a hot-link is established to a key in the ODB, immediately that key is accessed, a call-back routine associated with the hot-link is called to perform whatever action has been programmed. The MIDAS system uses hot-links to update keys in the ODB for communication between system clients  (e.g. [[History System]]).
 
   
 
   
 
Users often use hot-links to immediately set some hardware to a new value. The new value may have been input into  the ODB, either by the user or another client. Without a hot-link, the program setting the hardware values  would have to continually poll the ODB  to see if any values had changed; otherwise the new value would not be transmitted to the  hardware until the next time the ODB set values were read and applied (for example, at the beginning of a run).  
 
Users often use hot-links to immediately set some hardware to a new value. The new value may have been input into  the ODB, either by the user or another client. Without a hot-link, the program setting the hardware values  would have to continually poll the ODB  to see if any values had changed; otherwise the new value would not be transmitted to the  hardware until the next time the ODB set values were read and applied (for example, at the beginning of a run).  
  
== How to set up a Hot-Link ==
+
= How to set up a Hot-Link =
 
It is often desirable to modify hardware parameters (such as discriminator levels or trigger logic) connected to the frontend computer. Assuming that the required hardware is accessible from the frontend code, these parameters are easily controllable when a hot-link is established between the frontend and the ODB itself.
 
It is often desirable to modify hardware parameters (such as discriminator levels or trigger logic) connected to the frontend computer. Assuming that the required hardware is accessible from the frontend code, these parameters are easily controllable when a hot-link is established between the frontend and the ODB itself.
 +
 +
The following figure summarizes the components that are involved:
  
 
[[File:hotlink.gif|Hot-link process]]
 
[[File:hotlink.gif|Hot-link process]]
Line 27: Line 41:
  
 
The frontend can now map a C structure to these settings. In order to simplify this process,  [[odbedit]] can be requested to generate a header file containing this C structure.  
 
The frontend can now map a C structure to these settings. In order to simplify this process,  [[odbedit]] can be requested to generate a header file containing this C structure.  
The  odbedit command "make" generates in the current directory the header file ''experim.h'' .
+
The  [[odbedit]] command <span style="color:saddlebrown; font-style:italic;">"make"</span> generates in the current directory the header file ''experim.h'' .
  
 
This file can be copied to the frontend directory (if necessary) and included in the frontend source code. It contains a section with a C structure of the trigger settings and an ASCII representation:
 
This file can be copied to the frontend directory (if necessary) and included in the frontend source code. It contains a section with a C structure of the trigger settings and an ASCII representation:
Line 34: Line 48:
 
   INT      level1;
 
   INT      level1;
 
   INT      level2;
 
   INT      level2;
   )
+
   TRIGGER_SETTINGS;
  TRIGGER_SETTINGS;
+
      <br>
 
 
  #define TRIGGER_SETTINGS_STR(_name) char *_name[] = {\
 
  #define TRIGGER_SETTINGS_STR(_name) char *_name[] = {\
 
  "[.]",\
 
  "[.]",\
Line 42: Line 55:
 
  "level2 = INT : 0",\
 
  "level2 = INT : 0",\
 
  "",\
 
  "",\
  NULL  }
+
  NULL  
+
  }
 
 
 
This definition can be used to define a C structure containing the parameters in frontend.c:
 
This definition can be used to define a C structure containing the parameters in frontend.c:
 
 
  #include <experim.h>
 
  #include <experim.h>
 
  TRIGGER_SETTINGS trigger_settings;
 
  TRIGGER_SETTINGS trigger_settings;
 
 
 
A hot-link between the ODB values and the C structure is established in the frontend_init() routine:
 
A hot-link between the ODB values and the C structure is established in the frontend_init() routine:
 
 
  INT frontend_init()
 
  INT frontend_init()
 
  {
 
  {
 
   HNDLE hDB, hkey;
 
   HNDLE hDB, hkey;
 
   TRIGGER_SETTINGS_STR(trigger_settings_str);
 
   TRIGGER_SETTINGS_STR(trigger_settings_str);
                   //
+
                   <br>
 
   cm_get_experiment_database(&hDB, NULL);
 
   cm_get_experiment_database(&hDB, NULL);
                   //
+
                   <br>
 
   db_create_record(hDB, 0,
 
   db_create_record(hDB, 0,
 
     "/Equipment/Trigger/Settings",
 
     "/Equipment/Trigger/Settings",
 
     strcomb(trigger_settings_str));
 
     strcomb(trigger_settings_str));
                   //
+
                   <br>
 
   db_find_key(hDB, 0, "/Equipment/Trigger/Settings", &hkey);
 
   db_find_key(hDB, 0, "/Equipment/Trigger/Settings", &hkey);
                   //
+
                   <br>
 
   if (db_open_record(hDB, hkey,
 
   if (db_open_record(hDB, hkey,
 
       &trigger_settings,
 
       &trigger_settings,
Line 73: Line 81:
 
         return -1;
 
         return -1;
 
     }
 
     }
   
+
          <br>
 
   return SUCCESS;
 
   return SUCCESS;
 
  }  
 
  }  
 
 
The db_create_record() function re-creates the settings sub-tree in the ODB from the ASCII representation in case it has been corrupted or deleted.
 
The db_create_record() function re-creates the settings sub-tree in the ODB from the ASCII representation in case it has been corrupted or deleted.
 
The db_open_record() now establishes the hot-link between the settings in the ODB and the trigger_settings structure. Each time the ODB settings are modified, the changes are written to the trigger_settings structure and the callback routine trigger_update() is executed afterwards. This routine has the task to set the hardware according to the settings in the trigger_settings structure.
 
The db_open_record() now establishes the hot-link between the settings in the ODB and the trigger_settings structure. Each time the ODB settings are modified, the changes are written to the trigger_settings structure and the callback routine trigger_update() is executed afterwards. This routine has the task to set the hardware according to the settings in the trigger_settings structure.
  
 
It may look like:
 
It may look like:
 
 
  void trigger_update(INT hDB, INT hkey)
 
  void trigger_update(INT hDB, INT hkey)
 
  {
 
  {
Line 88: Line 94:
 
       trigger_settings.level2);
 
       trigger_settings.level2);
 
  }
 
  }
 
 
 
Of course the printf() function should be replaced by a function which accesses the hardware properly. Modifying the trigger values with [[odbedit]] can test the whole scheme:
 
Of course the printf() function should be replaced by a function which accesses the hardware properly. Modifying the trigger values with [[odbedit]] can test the whole scheme:
 
 
  [local]/>cd /Equipment/Trigger/Settings
 
  [local]/>cd /Equipment/Trigger/Settings
 
  [local]Settings>set level1 123
 
  [local]Settings>set level1 123
 
  [local]Settings>set level2 456
 
  [local]Settings>set level2 456
 
 
Immediately after each modification the frontend should display the new values.
 
Immediately after each modification the frontend should display the new values.
  
 +
<div id="odbedit save and load"></div>
 
The settings can be saved to a file and loaded back later:
 
The settings can be saved to a file and loaded back later:
 
 
  [local]/>cd /Equipment/Trigger/Settings
 
  [local]/>cd /Equipment/Trigger/Settings
 
  [local]Settings>save settings.odb
 
  [local]Settings>save settings.odb
Line 108: Line 110:
 
Following listing is a complete user application that modifies the trigger level:
 
Following listing is a complete user application that modifies the trigger level:
  
#include <midas.h>
+
#include <midas.h>
 
+
main()
main()
+
{
{
+
  HNDLE hDB;
HNDLE hDB;
+
  INT  level;
INT  level;
+
  cm_connect_experiment("", "Sample", "Test",
  cm_connect_experiment("", "Sample", "Test",
 
 
                         NULL);
 
                         NULL);
  cm_get_experiment_database(&hDB, NULL);
+
  cm_get_experiment_database(&hDB, NULL);
 
+
  <br>
  level = 321;
+
  level = 321;
  db_set_value(hDB, 0,
+
  db_set_value(hDB, 0,
 
     "/Equipment/Trigger/Settings/Level1",
 
     "/Equipment/Trigger/Settings/Level1",
 
     &level, sizeof(INT), 1, TID_INT);
 
     &level, sizeof(INT), 1, TID_INT);
 +
  <br>
 +
  cm_disconnect_experiment();
 +
  }
  
  cm_disconnect_experiment();
+
<div id="odbedit sor"></div>
 
+
To make sure a hot-link exists, one can use the [[odbedit]] command <span style="color:saddlebrown;font-style:italic; ">"sor"</span>  to show all open records, e.g.
The following figure summarizes the involved components:
 
 
 
To make sure a hot-link exists, one can use the [[odbedit]] command "sor"
 
  
 +
odbedit
 
  [local]Settings>cd /
 
  [local]Settings>cd /
 
  [local]/>sor
 
  [local]/>sor
   /Equipment/Trigger/Settings open 1 times by ...
+
   /Equipment/Trigger/Settings open 1 times by "fe_test"
 +
  ...
 +
 
 +
= Increasing number of hot-links =
 +
See [[Hotlink note]].
 +
 
 +
[[FAQ]]
 +
 
 +
= How hot links work =
 +
See [[Hotlink note]].
 +
 
 +
[[Category:Event]] [[Category:Hotlink]]

Latest revision as of 11:05, 25 November 2016


Links

Introduction

MIDAS implements event notification through "hot-links". Once a hot-link is established to a key in the ODB, immediately that key is accessed, a call-back routine associated with the hot-link is called to perform whatever action has been programmed. The MIDAS system uses hot-links to update keys in the ODB for communication between system clients (e.g. History System).

Users often use hot-links to immediately set some hardware to a new value. The new value may have been input into the ODB, either by the user or another client. Without a hot-link, the program setting the hardware values would have to continually poll the ODB to see if any values had changed; otherwise the new value would not be transmitted to the hardware until the next time the ODB set values were read and applied (for example, at the beginning of a run).

How to set up a Hot-Link

It is often desirable to modify hardware parameters (such as discriminator levels or trigger logic) connected to the frontend computer. Assuming that the required hardware is accessible from the frontend code, these parameters are easily controllable when a hot-link is established between the frontend and the ODB itself.

The following figure summarizes the components that are involved:

Hot-link process

First the parameters have to be defined in the ODB under the Settings tree for the given equipment. Let's assume we have two discriminator levels belonging to the trigger electronics, which should be controllable. The following commands define these levels in the ODB:

[local]/>cd /Equipment/Trigger/
[local]Trigger>create key Settings
[local]Trigger>cd Settings
[local]Settings>create int level1
[local]Settings>create int level2
[local]Settings>ls


The frontend can now map a C structure to these settings. In order to simplify this process, odbedit can be requested to generate a header file containing this C structure. The odbedit command "make" generates in the current directory the header file experim.h .

This file can be copied to the frontend directory (if necessary) and included in the frontend source code. It contains a section with a C structure of the trigger settings and an ASCII representation:

typedef struct {
 INT       level1;
 INT       level2;
 }  TRIGGER_SETTINGS;
     
#define TRIGGER_SETTINGS_STR(_name) char *_name[] = {\ "[.]",\ "level1 = INT : 0",\ "level2 = INT : 0",\ "",\ NULL }

This definition can be used to define a C structure containing the parameters in frontend.c:

#include <experim.h>
TRIGGER_SETTINGS trigger_settings;

A hot-link between the ODB values and the C structure is established in the frontend_init() routine:

INT frontend_init()
{
  HNDLE hDB, hkey;
  TRIGGER_SETTINGS_STR(trigger_settings_str);
                  
cm_get_experiment_database(&hDB, NULL);
db_create_record(hDB, 0, "/Equipment/Trigger/Settings", strcomb(trigger_settings_str));
db_find_key(hDB, 0, "/Equipment/Trigger/Settings", &hkey);
if (db_open_record(hDB, hkey, &trigger_settings, sizeof(trigger_settings), MODE_READ, trigger_update, NULL) != DB_SUCCESS) { cm_msg(MERROR, "frontend_init","Cannot open Trigger Settings in ODB"); return -1; }
return SUCCESS; }

The db_create_record() function re-creates the settings sub-tree in the ODB from the ASCII representation in case it has been corrupted or deleted. The db_open_record() now establishes the hot-link between the settings in the ODB and the trigger_settings structure. Each time the ODB settings are modified, the changes are written to the trigger_settings structure and the callback routine trigger_update() is executed afterwards. This routine has the task to set the hardware according to the settings in the trigger_settings structure.

It may look like:

void trigger_update(INT hDB, INT hkey)
{
   printf("New levels: %d %d",
     trigger_settings.level1,
     trigger_settings.level2);
}

Of course the printf() function should be replaced by a function which accesses the hardware properly. Modifying the trigger values with odbedit can test the whole scheme:

[local]/>cd /Equipment/Trigger/Settings
[local]Settings>set level1 123
[local]Settings>set level2 456

Immediately after each modification the frontend should display the new values.

The settings can be saved to a file and loaded back later:

[local]/>cd /Equipment/Trigger/Settings
[local]Settings>save settings.odb
[local]Settings>set level1 789
[local]Settings>load settings.odb

The settings can also be modified from any application just by accessing the ODB. Following listing is a complete user application that modifies the trigger level:

#include <midas.h>
main()
{
  HNDLE hDB;
  INT   level;
  cm_connect_experiment("", "Sample", "Test",
                       NULL);
  cm_get_experiment_database(&hDB, NULL);
  
level = 321; db_set_value(hDB, 0, "/Equipment/Trigger/Settings/Level1", &level, sizeof(INT), 1, TID_INT);
cm_disconnect_experiment(); }

To make sure a hot-link exists, one can use the odbedit command "sor" to show all open records, e.g.

odbedit
[local]Settings>cd /
[local]/>sor
 /Equipment/Trigger/Settings open 1 times by "fe_test"
 ...

Increasing number of hot-links

See Hotlink note.

FAQ

How hot links work

See Hotlink note.