update getmodules.c
[scilab.git] / scilab / modules / core / src / c / LoadFunctionsTab.c
1 /*-----------------------------------------------------------------------------------*/
2 /* INRIA 2006 */
3 /* Allan CORNET */
4 /*-----------------------------------------------------------------------------------*/
5 #include "MALLOC.h"
6 #include <stdlib.h>
7 #include <stdio.h>
8 #include <string.h>
9 #include <libxml/xpath.h>
10 #include <libxml/xmlreader.h>
11 #include "machine.h"
12 #include "hashtable_core.h"
13 #include "getmodules.h"
14 #include "setgetSCIpath.h"
15 #include "LoadFunctionsTab.h"
16 #include "GetXmlFileEncoding.h"
17 #include "../../fileio/includes/FileExist.h"
18 /*-----------------------------------------------------------------------------------*/  
19 static int firstentry = 0;
20 /*-----------------------------------------------------------------------------------*/  
21 extern int C2F(cvname) __PARAMS((integer *,char *,integer *, unsigned long int));
22 /*-----------------------------------------------------------------------------------*/  
23 static int Add_a_Scilab_primitive_in_hashtable(char *str, int *dataI, int *data);
24 static BOOL Load_primitives_from_file(char *filename);
25 /*-----------------------------------------------------------------------------------*/  
26 void LoadFunctionsTab(void)
27 {
28         struct MODULESLIST *Modules=NULL;
29         char *SciPath=NULL;
30         
31         int j=0;
32
33         if ( firstentry != 0 ) return;
34
35         SciPath=getSCIpath();
36         Modules=getmodules();
37         /* We are not freeing Modules in order to speed up the next call of getmodule */
38         /* freed in sciquit.c */
39
40         for (j=0;j<Modules->numberofModules;j++)
41         {
42                 #define FORMATFILENAME "%s/modules/%s/sci_gateway/%s_gateway.xml"
43                 char *filename_primitives_list=NULL;
44                 int len=strlen(FORMATFILENAME)+strlen(SciPath)+strlen(Modules->ModuleList[j])*2;
45
46                 filename_primitives_list=(char*)MALLOC((len+1)*sizeof(char));
47                 sprintf(filename_primitives_list,FORMATFILENAME,SciPath,Modules->ModuleList[j],Modules->ModuleList[j]);
48
49                 Load_primitives_from_file(filename_primitives_list);
50
51                 if (filename_primitives_list) { FREE(filename_primitives_list);filename_primitives_list=NULL;}
52         }
53
54         if (SciPath){FREE(SciPath);SciPath=NULL;}
55         firstentry = 1;
56
57 }
58 /*-----------------------------------------------------------------------------------*/
59 static int Add_a_Scilab_primitive_in_hashtable(char *str, int *dataI, int *data)
60 {
61         int ldata;
62         int id[nsiz];
63         int zero=0;
64         C2F(cvname)(id,str,&zero,strlen(str));
65         ldata= (*dataI)*100+*data;
66         return( action_hashtable_scilab_functions(id,str,&ldata,SCI_HFUNCTIONS_ENTER));
67 }
68 /*-----------------------------------------------------------------------------------*/
69 static BOOL Load_primitives_from_file(char *filename)
70 {
71         BOOL bOK=FALSE;
72
73         if (FileExist(filename))
74         {
75                 char *encoding=GetXmlFileEncoding(filename);
76
77                 /* Don't care about line return / empty line */
78                 xmlKeepBlanksDefault(0); 
79
80                 /* check if the XML file has been encoded with utf8 (unicode) or not */
81                 if ( (strcmp("utf-8", encoding)!=0) || (strcmp("UTF-8", encoding)==0) )
82                 {
83                         xmlDocPtr doc;
84                         xmlXPathContextPtr xpathCtxt = NULL;
85                         xmlXPathObjectPtr xpathObj = NULL;
86
87
88                         int GATEWAY_ID=0;
89                         int PRIMITIVE_ID=0;
90                         char *PRIMITIVE_NAME=NULL;
91
92                         doc = xmlParseFile (filename);
93
94                         if (doc == NULL) 
95                         {
96                                 printf("Error: could not parse file %s\n", filename);
97                                 if (encoding) {FREE(encoding);encoding=NULL;}
98                                 return bOK;
99                         }
100
101                         xpathCtxt = xmlXPathNewContext(doc);
102                         xpathObj = xmlXPathEval((const xmlChar*)"//GATEWAY/PRIMITIVE", xpathCtxt);
103
104                         if(xpathObj && xpathObj->nodesetval->nodeMax) 
105                         {
106                                 /* the Xpath has been understood and there are node */
107                                 int     i;
108                                 for(i = 0; i < xpathObj->nodesetval->nodeNr; i++)
109                                 {
110                                         xmlAttrPtr attrib=xpathObj->nodesetval->nodeTab[i]->properties;
111                                         /* Get the properties of <PRIMITIVE>  */
112                                         while (attrib != NULL)
113                                         {
114                                                 /* loop until when have read all the attributes */
115                                                 if (xmlStrEqual (attrib->name, (const xmlChar*) "gatewayId"))
116                                                 { 
117                                                         /* we found the tag gatewayId */
118                                                         const char *str=(const char*)attrib->children->content;
119                                                         GATEWAY_ID=atoi(str);
120                                                 }
121                                                 else if (xmlStrEqual (attrib->name, (const xmlChar*)"primitiveId"))
122                                                 { 
123                                                         /* we found the tag primitiveId */
124                                                         const char *str=(const char*)attrib->children->content;
125                                                         PRIMITIVE_ID=atoi(str);
126                                                 }
127                                                 else if (xmlStrEqual (attrib->name, (const xmlChar*)"primitiveName"))
128                                                 {
129                                                         /* we found the tag primitiveName */
130                                                         const char *str=(const char*)attrib->children->content;
131                                                         PRIMITIVE_NAME=(char*)MALLOC(sizeof(char)*(strlen((const char*)str)+1));
132                                                         strcpy(PRIMITIVE_NAME,str);
133                                                 }
134                                                 attrib = attrib->next;
135                                         }
136
137                                         if ( (GATEWAY_ID != 0) && (PRIMITIVE_ID != 0) && (PRIMITIVE_NAME) )
138                                         {
139                                                 if (strlen(PRIMITIVE_NAME) > 0)
140                                                 {
141                                                         Add_a_Scilab_primitive_in_hashtable(PRIMITIVE_NAME,&GATEWAY_ID,&PRIMITIVE_ID);
142                                                 }
143                                         }
144
145                                         if (PRIMITIVE_NAME) {FREE(PRIMITIVE_NAME); PRIMITIVE_NAME =NULL;}
146                                         GATEWAY_ID = 0;
147                                         PRIMITIVE_ID = 0;
148                                 }
149                         }
150                         else
151                         {
152                                 printf("Error : Not a valid gateway file %s (should start with <GATEWAY> and contains <PRIMITIVE gatewayId='' primitiveId='' primitiveName=''>)\n", filename);
153                                 return bOK;
154                         }
155                         if(xpathObj) xmlXPathFreeObject(xpathObj);
156                         if(xpathCtxt) xmlXPathFreeContext(xpathCtxt);
157                         xmlFreeDoc (doc);
158
159                         /*
160                         * Cleanup function for the XML library.
161                         */
162                         xmlCleanupParser();
163                 }
164                 else
165                 {
166                         printf("Error : Not a valid gateway file %s (encoding not 'utf-8') Encoding '%s' found\n", filename, encoding);
167                 }
168
169                 if (encoding) {FREE(encoding);encoding=NULL;}
170         }
171         return bOK;
172 }
173 /*-----------------------------------------------------------------------------------*/