Hello,
working to port PV engine to srouter, but also needed for kamailio's migration of pseudo-variables (PVs) from core to modules, I need to extend the module interface. The srouter has already support to work in dual mode committed by Andrei few days ago, so it should affect only kamailio's module interface if ser side does not need.
Here is the issue. In kamailio/openser we have so called transformations that are bound to PV. They are now implemented directly in core. To move them in a module, the interface needs to be extended, like we did in the past to export PVs from modules. The important aspect is that they must become visible immediately after the module is loaded -- this happens also with PVs (so cannot use mod_init, etc...). This is required because they may occur during script parsing, therefore the core/parser should get knowledge of them in very early stage.
PVs are exported via a specific structure in module interface. We can do same for transformations. There is another option, which can be used for other purposes in the future - introducing in module interface a callback to be run immediately after a module is loaded. The transformations can be exported inside the callback.
Extending this way, in the future, the modules can make other attributes visible to core/other modules immediately after loading without changing the module interface.
Therefore I would go for second option. Other opinions?
Cheers, Daniel
On Nov 20, 2008 at 11:50, Daniel-Constantin Mierla miconda@gmail.com wrote:
Hello,
working to port PV engine to srouter, but also needed for kamailio's migration of pseudo-variables (PVs) from core to modules, I need to extend the module interface. The srouter has already support to work in dual mode committed by Andrei few days ago, so it should affect only kamailio's module interface if ser side does not need.
Here is the issue. In kamailio/openser we have so called transformations that are bound to PV. They are now implemented directly in core. To move them in a module, the interface needs to be extended, like we did in the past to export PVs from modules. The important aspect is that they must become visible immediately after the module is loaded -- this happens also with PVs (so cannot use mod_init, etc...). This is required because they may occur during script parsing, therefore the core/parser should get knowledge of them in very early stage.
PVs are exported via a specific structure in module interface. We can do same for transformations. There is another option, which can be used for other purposes in the future - introducing in module interface a callback to be run immediately after a module is loaded. The transformations can be exported inside the callback.
I personally don't like extending the module_export structure. It was done a lot in the past (both in kamailio/openser and ser), but IMHO is a mistake, because then you have to update _all_ the module to the new interface or do some hack like we have in sip-router to support several module interface versions. Instead of extending the structure is better to either add a new one an look (dlsym) for it when loading a module (if it's not present we just assume the module doesn't implement it), or use a callback.
Extending this way, in the future, the modules can make other attributes visible to core/other modules immediately after loading without changing the module interface.
Therefore I would go for second option. Other opinions?
I prefer the callback too. As a matter of fact the first ser versions used to have a mod_register function for exactly that purpose: the module loader would resolve the mod_register symbol (dlsym()) and then call it. In the first versions mod_register would also add/register the module_export structure (which was not automatically loaded).
I was going to propose mod_register revival too, for slightly different reasons: - IMHO the mod_export structure is too big and some parts of it are used only by a few modules, so I think it's easier/nicer to keep it smaller and register the not so common stuff from mod_register. - using this callback mechanism is easy to extend mod_export in the future without requiring _any_ change in modules who don't implement / don't care for the new functionality. - on some system it seems not to be possible to resolve a symbol pointing to a data structure, only symbols pointing to functions are ok (that and windows are on of the reasons for the static modules compilation options). So if we ever decide to fully support such systems we might need to register everything from mod_register even the module_export structure (we could make some macro that would do this semi-automatically). - one could dynamically manipulate mod_exports, before it's register (e.g. change pointer to functions depending on whether or not the system is smp :-)).
So as first step I would add support for looking for and executing mod_register when loading the modules, before resolving/registering mod_export. The prototype for it would look like: int mod_register(char* path, int* dlflags) (it's better to do the dlflags hack as soon as possible) ret < 0 => don't load the module, 0 success, >0 reserved for future use.
Does anybody disagree? Do you have a better name, or better prototype proposal?
No _quick_ answer will be considered agreement (we can easily change it latter anyway if only a few module use it).
Andrei
On 11/20/08 12:40, Andrei Pelinescu-Onciul wrote:
On Nov 20, 2008 at 11:50, Daniel-Constantin Mierla miconda@gmail.com wrote:
Hello,
working to port PV engine to srouter, but also needed for kamailio's migration of pseudo-variables (PVs) from core to modules, I need to extend the module interface. The srouter has already support to work in dual mode committed by Andrei few days ago, so it should affect only kamailio's module interface if ser side does not need.
Here is the issue. In kamailio/openser we have so called transformations that are bound to PV. They are now implemented directly in core. To move them in a module, the interface needs to be extended, like we did in the past to export PVs from modules. The important aspect is that they must become visible immediately after the module is loaded -- this happens also with PVs (so cannot use mod_init, etc...). This is required because they may occur during script parsing, therefore the core/parser should get knowledge of them in very early stage.
PVs are exported via a specific structure in module interface. We can do same for transformations. There is another option, which can be used for other purposes in the future - introducing in module interface a callback to be run immediately after a module is loaded. The transformations can be exported inside the callback.
I personally don't like extending the module_export structure. It was done a lot in the past (both in kamailio/openser and ser), but IMHO is a mistake, because then you have to update _all_ the module to the new interface or do some hack like we have in sip-router to support several module interface versions. Instead of extending the structure is better to either add a new one an look (dlsym) for it when loading a module (if it's not present we just assume the module doesn't implement it), or use a callback.
Extending this way, in the future, the modules can make other attributes visible to core/other modules immediately after loading without changing the module interface.
Therefore I would go for second option. Other opinions?
I prefer the callback too. As a matter of fact the first ser versions used to have a mod_register function for exactly that purpose: the module loader would resolve the mod_register symbol (dlsym()) and then call it. In the first versions mod_register would also add/register the module_export structure (which was not automatically loaded).
I was going to propose mod_register revival too, for slightly different reasons:
- IMHO the mod_export structure is too big and some parts of it are used only by a few modules, so I think it's easier/nicer to keep it smaller and register the not so common stuff from mod_register.
- using this callback mechanism is easy to extend mod_export in the future without requiring _any_ change in modules who don't implement / don't care for the new functionality.
- on some system it seems not to be possible to resolve a symbol pointing
to a data structure, only symbols pointing to functions are ok (that and windows are on of the reasons for the static modules compilation options). So if we ever decide to fully support such systems we might need to register everything from mod_register even the module_export structure (we could make some macro that would do this semi-automatically).
- one could dynamically manipulate mod_exports, before it's register
(e.g. change pointer to functions depending on whether or not the system is smp :-)).
So as first step I would add support for looking for and executing mod_register when loading the modules, before resolving/registering mod_export. The prototype for it would look like: int mod_register(char* path, int* dlflags) (it's better to do the dlflags hack as soon as possible) ret < 0 => don't load the module, 0 success, >0 reserved for future use.
Does anybody disagree? Do you have a better name, or better prototype proposal?
No _quick_ answer will be considered agreement (we can easily change it latter anyway if only a few module use it).
mod_register sounds good.
I was looking to keep everything in module_exports structure, just for consistency. But this indeed requires a lot of updates upon small change there.
As you say, from perspective of portability, exporting by function is better.
What would be the meaning of path parameter in mod_register? The module name?
Cheers, Daniel
On Nov 20, 2008 at 12:53, Daniel-Constantin Mierla miconda@gmail.com wrote:
On 11/20/08 12:40, Andrei Pelinescu-Onciul wrote:
On Nov 20, 2008 at 11:50, Daniel-Constantin Mierla miconda@gmail.com wrote:
Hello,
working to port PV engine to srouter, but also needed for kamailio's migration of pseudo-variables (PVs) from core to modules, I need to extend the module interface. The srouter has already support to work in dual mode committed by Andrei few days ago, so it should affect only kamailio's module interface if ser side does not need.
Here is the issue. In kamailio/openser we have so called transformations that are bound to PV. They are now implemented directly in core. To move them in a module, the interface needs to be extended, like we did in the past to export PVs from modules. The important aspect is that they must become visible immediately after the module is loaded -- this happens also with PVs (so cannot use mod_init, etc...). This is required because they may occur during script parsing, therefore the core/parser should get knowledge of them in very early stage.
PVs are exported via a specific structure in module interface. We can do same for transformations. There is another option, which can be used for other purposes in the future - introducing in module interface a callback to be run immediately after a module is loaded. The transformations can be exported inside the callback.
I personally don't like extending the module_export structure. It was done a lot in the past (both in kamailio/openser and ser), but IMHO is a mistake, because then you have to update _all_ the module to the new interface or do some hack like we have in sip-router to support several module interface versions. Instead of extending the structure is better to either add a new one an look (dlsym) for it when loading a module (if it's not present we just assume the module doesn't implement it), or use a callback.
Extending this way, in the future, the modules can make other attributes visible to core/other modules immediately after loading without changing the module interface.
Therefore I would go for second option. Other opinions?
I prefer the callback too. As a matter of fact the first ser versions used to have a mod_register function for exactly that purpose: the module loader would resolve the mod_register symbol (dlsym()) and then call it. In the first versions mod_register would also add/register the module_export structure (which was not automatically loaded).
I was going to propose mod_register revival too, for slightly different reasons:
- IMHO the mod_export structure is too big and some parts of it are used only by a few modules, so I think it's easier/nicer to keep it smaller and register the not so common stuff from mod_register.
- using this callback mechanism is easy to extend mod_export in the
future without requiring _any_ change in modules who don't implement / don't care for the new functionality.
- on some system it seems not to be possible to resolve a symbol pointing
to a data structure, only symbols pointing to functions are ok (that and windows are on of the reasons for the static modules compilation options). So if we ever decide to fully support such systems we might need to register everything from mod_register even the module_export structure (we could make some macro that would do this semi-automatically).
- one could dynamically manipulate mod_exports, before it's register
(e.g. change pointer to functions depending on whether or not the system is smp :-)).
So as first step I would add support for looking for and executing mod_register when loading the modules, before resolving/registering mod_export. The prototype for it would look like: int mod_register(char* path, int* dlflags) (it's better to do the dlflags hack as soon as possible) ret < 0 => don't load the module, 0 success, >0 reserved for future use.
Does anybody disagree? Do you have a better name, or better prototype proposal?
No _quick_ answer will be considered agreement (we can easily change it latter anyway if only a few module use it).
mod_register sounds good.
I was looking to keep everything in module_exports structure, just for consistency. But this indeed requires a lot of updates upon small change there.
As you say, from perspective of portability, exporting by function is better.
What would be the meaning of path parameter in mod_register? The module name?
The path including the module name (what was passed to dlopen). It might be usefull in some corner cases (like module who wants to load another module/plugin).
Andrei
On 11/20/08 12:58, Andrei Pelinescu-Onciul wrote:
On Nov 20, 2008 at 12:53, Daniel-Constantin Mierla miconda@gmail.com wrote:
On 11/20/08 12:40, Andrei Pelinescu-Onciul wrote:
On Nov 20, 2008 at 11:50, Daniel-Constantin Mierla miconda@gmail.com wrote:
Hello,
working to port PV engine to srouter, but also needed for kamailio's migration of pseudo-variables (PVs) from core to modules, I need to extend the module interface. The srouter has already support to work in dual mode committed by Andrei few days ago, so it should affect only kamailio's module interface if ser side does not need.
Here is the issue. In kamailio/openser we have so called transformations that are bound to PV. They are now implemented directly in core. To move them in a module, the interface needs to be extended, like we did in the past to export PVs from modules. The important aspect is that they must become visible immediately after the module is loaded -- this happens also with PVs (so cannot use mod_init, etc...). This is required because they may occur during script parsing, therefore the core/parser should get knowledge of them in very early stage.
PVs are exported via a specific structure in module interface. We can do same for transformations. There is another option, which can be used for other purposes in the future - introducing in module interface a callback to be run immediately after a module is loaded. The transformations can be exported inside the callback.
I personally don't like extending the module_export structure. It was done a lot in the past (both in kamailio/openser and ser), but IMHO is a mistake, because then you have to update _all_ the module to the new interface or do some hack like we have in sip-router to support several module interface versions. Instead of extending the structure is better to either add a new one an look (dlsym) for it when loading a module (if it's not present we just assume the module doesn't implement it), or use a callback.
Extending this way, in the future, the modules can make other attributes visible to core/other modules immediately after loading without changing the module interface.
Therefore I would go for second option. Other opinions?
I prefer the callback too. As a matter of fact the first ser versions used to have a mod_register function for exactly that purpose: the module loader would resolve the mod_register symbol (dlsym()) and then call it. In the first versions mod_register would also add/register the module_export structure (which was not automatically loaded).
I was going to propose mod_register revival too, for slightly different reasons:
- IMHO the mod_export structure is too big and some parts of it are used only by a few modules, so I think it's easier/nicer to keep it smaller and register the not so common stuff from mod_register.
- using this callback mechanism is easy to extend mod_export in the
future without requiring _any_ change in modules who don't implement / don't care for the new functionality.
- on some system it seems not to be possible to resolve a symbol pointing
to a data structure, only symbols pointing to functions are ok (that and windows are on of the reasons for the static modules compilation options). So if we ever decide to fully support such systems we might need to register everything from mod_register even the module_export structure (we could make some macro that would do this semi-automatically).
- one could dynamically manipulate mod_exports, before it's register
(e.g. change pointer to functions depending on whether or not the system is smp :-)).
So as first step I would add support for looking for and executing mod_register when loading the modules, before resolving/registering mod_export. The prototype for it would look like: int mod_register(char* path, int* dlflags) (it's better to do the dlflags hack as soon as possible) ret < 0 => don't load the module, 0 success, >0 reserved for future use.
Does anybody disagree? Do you have a better name, or better prototype proposal?
No _quick_ answer will be considered agreement (we can easily change it latter anyway if only a few module use it).
mod_register sounds good.
I was looking to keep everything in module_exports structure, just for consistency. But this indeed requires a lot of updates upon small change there.
As you say, from perspective of portability, exporting by function is better.
What would be the meaning of path parameter in mod_register? The module name?
The path including the module name (what was passed to dlopen). It might be usefull in some corner cases (like module who wants to load another module/plugin).
ok, btw, kamailio modules export also the dlflags needed to open the object -- required by perl module -- this should be kept in mind.
Cheers, Daniel
On Nov 20, 2008 at 13:06, Daniel-Constantin Mierla miconda@gmail.com wrote:
On 11/20/08 12:58, Andrei Pelinescu-Onciul wrote:
On Nov 20, 2008 at 12:53, Daniel-Constantin Mierla miconda@gmail.com wrote:
On 11/20/08 12:40, Andrei Pelinescu-Onciul wrote:
On Nov 20, 2008 at 11:50, Daniel-Constantin Mierla miconda@gmail.com wrote:
Hello,
working to port PV engine to srouter, but also needed for kamailio's migration of pseudo-variables (PVs) from core to modules, I need to extend the module interface. The srouter has already support to work in dual mode committed by Andrei few days ago, so it should affect only kamailio's module interface if ser side does not need.
Here is the issue. In kamailio/openser we have so called transformations that are bound to PV. They are now implemented directly in core. To move them in a module, the interface needs to be extended, like we did in the past to export PVs from modules. The important aspect is that they must become visible immediately after the module is loaded -- this happens also with PVs (so cannot use mod_init, etc...). This is required because they may occur during script parsing, therefore the core/parser should get knowledge of them in very early stage.
PVs are exported via a specific structure in module interface. We can do same for transformations. There is another option, which can be used for other purposes in the future - introducing in module interface a callback to be run immediately after a module is loaded. The transformations can be exported inside the callback.
I personally don't like extending the module_export structure. It was done a lot in the past (both in kamailio/openser and ser), but IMHO is a mistake, because then you have to update _all_ the module to the new interface or do some hack like we have in sip-router to support several module interface versions. Instead of extending the structure is better to either add a new one an look (dlsym) for it when loading a module (if it's not present we just assume the module doesn't implement it), or use a callback.
Extending this way, in the future, the modules can make other attributes visible to core/other modules immediately after loading without changing the module interface.
Therefore I would go for second option. Other opinions?
I prefer the callback too. As a matter of fact the first ser versions used to have a mod_register function for exactly that purpose: the module loader would resolve the mod_register symbol (dlsym()) and then call it. In the first versions mod_register would also add/register the module_export structure (which was not automatically loaded).
I was going to propose mod_register revival too, for slightly different reasons:
- IMHO the mod_export structure is too big and some parts of it are
used only by a few modules, so I think it's easier/nicer to keep it smaller and register the not so common stuff from mod_register.
- using this callback mechanism is easy to extend mod_export in the
future without requiring _any_ change in modules who don't implement / don't care for the new functionality.
- on some system it seems not to be possible to resolve a symbol
pointing to a data structure, only symbols pointing to functions are ok (that and windows are on of the reasons for the static modules compilation options). So if we ever decide to fully support such systems we might need to register everything from mod_register even the module_export structure (we could make some macro that would do this semi-automatically).
- one could dynamically manipulate mod_exports, before it's register
(e.g. change pointer to functions depending on whether or not the system is smp :-)).
So as first step I would add support for looking for and executing mod_register when loading the modules, before resolving/registering mod_export. The prototype for it would look like: int mod_register(char* path, int* dlflags) (it's better to do the dlflags hack as soon as possible) ret < 0 => don't load the module, 0 success, >0 reserved for future use.
Does anybody disagree? Do you have a better name, or better prototype proposal?
No _quick_ answer will be considered agreement (we can easily change it latter anyway if only a few module use it).
mod_register sounds good.
I was looking to keep everything in module_exports structure, just for consistency. But this indeed requires a lot of updates upon small change there.
As you say, from perspective of portability, exporting by function is better.
What would be the meaning of path parameter in mod_register? The module name?
The path including the module name (what was passed to dlopen). It might be usefull in some corner cases (like module who wants to load another module/plugin).
ok, btw, kamailio modules export also the dlflags needed to open the object -- required by perl module -- this should be kept in mind.
That's why I added it in the prototype, I want to obsolete that (if in mod_exports and !=0 or !=default WARN consider moving it in...). It should be either in mod_register or maybe a separate export.
Andrei