OSDN Git Service

git-svn-id: http://svn.osdn.jp/svnroot/mimic/trunk@198 47198e57-cb75-475f-84c4-a814cd...
[mimic/MiMicSDK.git] / lib / src / net / httpd / mod / NyLPC_cModRemoteMcu.c
1 /*********************************************************************************\r
2  * PROJECT: MiMic\r
3  * --------------------------------------------------------------------------------\r
4  *\r
5  * This file is part of MiMic\r
6  * Copyright (C)2011 Ryo Iizuka\r
7  *\r
8  * MiMic is free software: you can redistribute it and/or modify\r
9  * it under the terms of the GNU Lesser General Public License as published\r
10  * by the Free Software Foundation, either version 3 of the License, or\r
11  * (at your option) any later version.\r
12  *\r
13  * This program is distributed in the hope that it will be useful,\r
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of\r
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\r
16  * GNU General Public License for more details.\r
17  *\r
18  * You should have received a copy of the GNU Lesser General Public License\r
19  * along with this program.  If not, see <http://www.gnu.org/licenses/>.\r
20  *\r
21  * For further information please contact.\r
22  *      http://nyatla.jp/\r
23  *      <airmail(at)ebony.plala.or.jp> or <nyatla(at)nyatla.jp>\r
24  *\r
25  *********************************************************************************/\r
26 #include "NyLPC_cModRemoteMcu.h"\r
27 #include "NyLPC_stdlib.h"\r
28 #include "../http/NyLPC_cHttpShortRequestHeaderParser.h"\r
29 #include "../NyLPC_cHttpdConnection_protected.h"\r
30 #include "../../../mimicvm/NyLPC_cMiMicDbCompiler.h"\r
31 #include "../../../mimicvm/NyLPC_cMiMicTxtCompiler.h"\r
32 #include "NyLPC_cHttpmodUtils_protected.h"\r
33 #include "../../../mimicvm/NyLPC_cMiMicVM_protected.h"\r
34 \r
35 \r
36 #define MVM_VERSION "MiMicVM/1.0;Json/1.0"\r
37 #define SIZE_OF_IBUF 256\r
38 struct TModMiMicRemoteMcuHeader\r
39 {\r
40         struct NyLPC_THttpBasicHeader super;\r
41         NyLPC_TUInt8 _content_id;\r
42         //解析用\r
43         NyLPC_TUInt8 _qery_name_id;\r
44         NyLPC_TUInt16 _prefix_len;\r
45         NyLPC_TUInt8 _astate;\r
46         NyLPC_TcStr_t _tstr;\r
47         NyLPC_TChar _tstr_buf[16];\r
48         struct NyLPC_TUInt32ArrayPtr _binarray;\r
49         /** 文字列のパーサ*/\r
50         NyLPC_TcMiMicDbCompiler_t _binparser;\r
51         NyLPC_TcMiMicTxtCompiler_t _txtcmp;\r
52         union{\r
53                 struct{\r
54                         NyLPC_TUInt8 v;//バージョン\r
55                         NyLPC_TUInt8 o;//outputスタイル\r
56                         /**\r
57                          * il_bufはbcとdbの2パートのデータを格納します。\r
58                          * 先頭からbc_lenの長さのBCパートと、db_partからdb_lenの長さのデータです。\r
59                          */\r
60                         struct{\r
61                                 /** MiMicVMインストラクションの蓄積用。前半にTXT,後半にDBを格納する。 */\r
62                                 NyLPC_TUInt32 bc_buf[SIZE_OF_IBUF];\r
63                                 /** MiMicVM入力ストリーム(MimicDB)の開始位置(bufの一部を指す) */\r
64                                 const NyLPC_TUInt32* db_part;\r
65                                 /** MiMicTXTのワード長(1ワード32bit)*/\r
66                                 NyLPC_TUInt16 txt_len;\r
67                                 /** MiMicDBのワード長(1ワード32bit)*/\r
68                                 NyLPC_TUInt16 db_len;\r
69                         }vm_instruction;\r
70                 }mvm;\r
71                 struct{\r
72                         /**\r
73                          * 不明な名前の場合は、ここに名前をコピー\r
74                          */\r
75                         NyLPC_TChar path[32];\r
76                 }unknown;\r
77         }content;\r
78 };\r
79 \r
80 \r
81 static void mvm(NyLPC_TcHttpdConnection_t* i_connection,const struct TModMiMicRemoteMcuHeader* i_rqh);\r
82 \r
83 \r
84 static NyLPC_TBool messageHandler(NyLPC_TcHttpBasicHeaderParser_t* i_inst,const NyLPC_TChar* i_name,NyLPC_TChar i_c,struct NyLPC_THttpBasicHeader* o_out)\r
85 {\r
86         (void)i_inst;\r
87         (void)i_name;\r
88         (void)i_c;\r
89         return NyLPC_TBool_TRUE;\r
90 }\r
91 \r
92 #define ST_PARSE_PATH 1\r
93 #define ST_PARSE_QUERY_NAME 2\r
94 #define ST_PARSE_QUERY_VALUE 3          //Query読み出し中\r
95 #define ST_PARSE_QUERY_VALUE_V 4\r
96 #define ST_PARSE_QUERY_VALUE_O 5\r
97 #define ST_PARSE_QUERY_VALUE_BC 6\r
98 #define ST_PARSE_QUERY_VALUE_DB 7\r
99 /**\r
100  * コンテンツID定義(コンテンツ名に対応)\r
101  */\r
102 #define CONTENT_ID_MVM   2\r
103 #define CONTENT_ID_STATUS  3\r
104 #define CONTENT_ID_UNKNOWN 0\r
105 \r
106 \r
107 #define QNAME_ID_V      1\r
108 #define QNAME_ID_O      2\r
109 #define QNAME_ID_BC     3\r
110 #define QNAME_ID_UNKNOWN 0\r
111 \r
112 /**\r
113  * TRemoteMcuRequest.content.mvm.oの値\r
114  */\r
115 #define QVAL_O_UNKNOWN 0        //default\r
116 #define QVAL_O_XML     1\r
117 #define QVAL_O_JSON    2\r
118 \r
119 #define QVAL_V_UNKNOWN  0\r
120 #define QVAL_V_1        1\r
121 \r
122 \r
123 const struct NyLPC_TTextIdTbl url_tbl[]=\r
124 {\r
125         {"mvm.api",CONTENT_ID_MVM},\r
126         {"status.api",CONTENT_ID_STATUS},\r
127         {NULL,CONTENT_ID_UNKNOWN}\r
128 };\r
129 \r
130 const struct NyLPC_TTextIdTbl qname_id_table[]=\r
131 {\r
132         {"o",QNAME_ID_O},\r
133         {"bc",QNAME_ID_BC},\r
134         {"v",QNAME_ID_V},\r
135         {NULL,QNAME_ID_UNKNOWN}\r
136 };\r
137 \r
138 \r
139 \r
140 static NyLPC_TBool urlHandler(NyLPC_TcHttpBasicHeaderParser_t* i_inst,NyLPC_TChar i_c,struct NyLPC_THttpBasicHeader* o_out)\r
141 {\r
142         NyLPC_TUInt16 ol;\r
143         struct TModMiMicRemoteMcuHeader* out=(struct TModMiMicRemoteMcuHeader*)o_out;\r
144         //読み飛ばし\r
145         if(out->_prefix_len<0){\r
146                 out->_prefix_len++;\r
147                 return NyLPC_TBool_TRUE;//読み飛ばし\r
148         }\r
149         if(out->_astate==ST_PARSE_PATH){\r
150                 switch(i_c){\r
151                 case '\0':\r
152                 case '?':\r
153                         out->_content_id=NyLPC_TTextIdTbl_getMatchId(NyLPC_cStr_str(&(out->_tstr)),url_tbl);\r
154                         switch(out->_content_id)\r
155                         {\r
156                         case CONTENT_ID_MVM:\r
157                                 out->content.mvm.vm_instruction.txt_len=0;\r
158                                 out->content.mvm.vm_instruction.db_len=0;\r
159                                 out->content.mvm.vm_instruction.db_part=NULL;\r
160                                 NyLPC_TUInt32ArrayPtr_setBuf(&out->_binarray,out->content.mvm.vm_instruction.bc_buf,SIZE_OF_IBUF);\r
161                                 out->content.mvm.o=QVAL_O_UNKNOWN;\r
162                                 out->content.mvm.v=QVAL_V_UNKNOWN;\r
163                                 break;\r
164                         default:\r
165                                 break;\r
166                         }\r
167 \r
168                         NyLPC_cStr_clear(&(out->_tstr));\r
169                         out->_astate=ST_PARSE_QUERY_NAME;//クエリ名解析へ\r
170                         return NyLPC_TBool_TRUE;\r
171                 default:\r
172                         break;\r
173                 }\r
174                 return NyLPC_TBool_TRUE;\r
175         }\r
176         switch(out->_content_id)\r
177         {\r
178         case CONTENT_ID_MVM:\r
179                 switch(out->_astate){\r
180                 case ST_PARSE_QUERY_NAME:\r
181                         if(i_c!='\0' && i_c!='&' && i_c!='='){\r
182                                 if(!NyLPC_cStr_put(&(out->_tstr),i_c)){\r
183                                         NyLPC_OnErrorGoto(ERROR);\r
184                                 }\r
185                                 return NyLPC_TBool_TRUE;\r
186                         }\r
187                         //Query確定。\r
188                         out->_qery_name_id=NyLPC_TTextIdTbl_getMatchId(NyLPC_cStr_str(&(out->_tstr)),qname_id_table);\r
189                         NyLPC_cStr_clear(&(out->_tstr));\r
190                         //クエリ値がある場合\r
191                         switch(out->_qery_name_id){\r
192                         case QNAME_ID_O:\r
193                                 out->_astate=ST_PARSE_QUERY_VALUE_O;//MIMICBCのDBパラメータパーサを借用。\r
194                                 break;\r
195                         case QNAME_ID_V:\r
196                                 out->_astate=ST_PARSE_QUERY_VALUE_V;\r
197                                 break;\r
198                         case QNAME_ID_BC:\r
199                                 out->_astate=ST_PARSE_QUERY_VALUE_BC;\r
200                                 break;\r
201                         default:\r
202                                 out->_astate=ST_PARSE_QUERY_VALUE;\r
203                                 break;\r
204                         }\r
205                         return NyLPC_TBool_TRUE;\r
206                 case ST_PARSE_QUERY_VALUE:\r
207                         //未知のクエリは無視\r
208                         if(i_c!='\0' || i_c!='&'){\r
209                                 return NyLPC_TBool_TRUE;\r
210                         }\r
211                         //クエリ値解析完了\r
212                         out->_astate=ST_PARSE_QUERY_NAME;\r
213                         return NyLPC_TBool_TRUE;\r
214                 case ST_PARSE_QUERY_VALUE_O:\r
215                         if(i_c!='\0' || i_c!='&'){\r
216                                 if(!NyLPC_cStr_put(&(out->_tstr),i_c)){\r
217                                         NyLPC_OnErrorGoto(ERROR);\r
218                                 }\r
219                                 return NyLPC_TBool_TRUE;\r
220                         }\r
221                         if(NyLPC_cStr_isEqual(&(out->_tstr),"j")){\r
222                                 out->content.mvm.o=QVAL_O_JSON;\r
223                         }else if(NyLPC_cStr_isEqual(&(out->_tstr),"x")){\r
224                                 out->content.mvm.o=QVAL_O_XML;\r
225                         }\r
226                         out->_astate=ST_PARSE_QUERY_NAME;\r
227                         return NyLPC_TBool_TRUE;\r
228                 case ST_PARSE_QUERY_VALUE_V:\r
229                         if(i_c!='\0' || i_c!='&'){\r
230                                 if(!NyLPC_cStr_put(&(out->_tstr),i_c)){\r
231                                         NyLPC_OnErrorGoto(ERROR);\r
232                                 }\r
233                                 return NyLPC_TBool_TRUE;\r
234                         }\r
235                         if(NyLPC_cStr_isEqual(&(out->_tstr),"1")){\r
236                                 out->content.mvm.v=QVAL_V_1;\r
237                         }\r
238                         out->_astate=ST_PARSE_QUERY_NAME;\r
239                         return NyLPC_TBool_TRUE;\r
240                 case ST_PARSE_QUERY_VALUE_BC:\r
241                         if(i_c!='\0' || i_c!='&'){\r
242                                 //コンパイル\r
243                                 switch(NyLPC_cMiMicTxtCompiler_compileFragment2(&(out->_txtcmp),i_c,&(out->_binarray),&ol))\r
244                                 {\r
245                                 case NyLPC_TcMiMicTxtCompiler_RET_OK:\r
246                                         //命令確定。\r
247                                         break;\r
248                                 case NyLPC_TcMiMicTxtCompiler_RET_OK_END:\r
249                                         //命令終端検出->モード切替\r
250                                         out->content.mvm.vm_instruction.txt_len=SIZE_OF_IBUF-out->_binarray.len+ol;\r
251                                         out->content.mvm.vm_instruction.db_part=out->content.mvm.vm_instruction.bc_buf+out->content.mvm.vm_instruction.txt_len;\r
252                                         out->_astate=ST_PARSE_QUERY_VALUE_DB;\r
253                                         break;\r
254                                 case NyLPC_TcMiMicTxtCompiler_RET_CONTINUE:\r
255                                         //何もしない\r
256                                         break;\r
257                                 case NyLPC_TcMiMicTxtCompiler_RET_NG:\r
258                                 default:\r
259                                         //ERROR\r
260                                         NyLPC_OnErrorGoto(ERROR);\r
261                                 }\r
262                                 return NyLPC_TBool_TRUE;\r
263                         }\r
264                         //フラグメント終端が検出できない終了はエラー\r
265                         NyLPC_OnErrorGoto(ERROR);\r
266                 case ST_PARSE_QUERY_VALUE_DB:\r
267                         if(i_c!='\0' || i_c!='&'){\r
268                                 switch(NyLPC_cMiMicDbCompiler_compileFragment2(&(out->_binparser),i_c,out->_binarray.ptr))\r
269                                 {\r
270                                 case NyLPC_TcMiMicDbCompiler_RET_CONTINUE:\r
271                                         break;\r
272                                 case NyLPC_TcMiMicDbCompiler_RET_OK:\r
273                                         //\r
274                                         if(!NyLPC_TUInt32ArrayPtr_seek(&(out->_binarray),1)){\r
275                                                 //ERROR\r
276                                                 NyLPC_OnErrorGoto(ERROR);\r
277                                         }\r
278                                         break;\r
279                                 case NyLPC_TcMiMicDbCompiler_RET_ERROR:\r
280                                 default:\r
281                                         //ERROR\r
282                                         NyLPC_OnErrorGoto(ERROR);\r
283                                 }\r
284                                 return NyLPC_TBool_TRUE;\r
285                         }\r
286                         //区切りのいいところで終わってる?\r
287                         if(NyLPC_cMiMicDbCompiler_hasFragment(&(out->_binparser))){\r
288                                 //ERROR\r
289                                 NyLPC_OnErrorGoto(ERROR);\r
290                         }\r
291                         //終端しているなら、次のクエリへ\r
292                         out->_astate=ST_PARSE_QUERY_NAME;\r
293                         return NyLPC_TBool_TRUE;\r
294                 default:\r
295                         break;\r
296                 }\r
297                 NyLPC_OnErrorGoto(ERROR);\r
298         default:\r
299                 NyLPC_OnErrorGoto(ERROR);\r
300         }\r
301         return NyLPC_TBool_TRUE;\r
302 ERROR:\r
303         return NyLPC_TBool_FALSE;\r
304 }\r
305 /**\r
306  * デフォルトハンドラ\r
307  */\r
308 static const struct NyLPC_TcHttpBasicHeaderParser_Handler handler=\r
309 {\r
310         messageHandler,\r
311         urlHandler\r
312 };\r
313 \r
314 \r
315 /**\r
316  * コンストラクタ。\r
317  */\r
318 void NyLPC_cModMiMicSetting_initialize(NyLPC_TcModRemoteMcu_t* i_inst,const NyLPC_TChar* i_ref_root_path)\r
319 {\r
320         NyLPC_cModRomFiles_initialize(&i_inst->super,i_ref_root_path,NULL,0);\r
321 }\r
322 void NyLPC_cModMiMicSetting_finalize(NyLPC_TcModRemoteMcu_t* i_inst)\r
323 {\r
324         NyLPC_cModRomFiles_finalize(&i_inst->super);\r
325 }\r
326 /**\r
327  * モジュールがコネクションをハンドリングできるかを返します。\r
328  */\r
329 NyLPC_TBool NyLPC_cModMiMicSetting_canHandle(NyLPC_TcModRemoteMcu_t* i_inst,NyLPC_TcHttpdConnection_t* i_connection)\r
330 {\r
331         return NyLPC_cModRomFiles_canHandle(&i_inst->super,i_connection);\r
332 }\r
333 \r
334 /**\r
335  * モジュールを実行します。\r
336  */\r
337 NyLPC_TBool NyLPC_cModMiMicSetting_execute(NyLPC_TcModRemoteMcu_t* i_inst,NyLPC_TcHttpdConnection_t* i_connection,const NyLPC_TChar* i_root_path)\r
338 {\r
339         struct TModMiMicRemoteMcuHeader header;\r
340         NyLPC_TcHttpBasicHeaderParser_t parser;\r
341         //connectonの状態を確認\r
342         if(!NyLPC_cHttpdConnection_getReqStatus(i_connection)==NyLPC_cHttpdConnection_ReqStatus_REQPARSE)\r
343         {\r
344                 NyLPC_OnErrorGoto(Error1);\r
345         }\r
346 //リソース占有\r
347         //VM起動の為の排他ロック\r
348         NyLPC_cHttpdConnection_lock(i_connection);\r
349 \r
350 \r
351         //URL解析の準備\r
352         header._prefix_len=-(NyLPC_TInt16)strlen(i_inst->super._ref_root_path);\r
353         header._astate=ST_PARSE_PATH;\r
354         NyLPC_cStr_initialize(&header._tstr,header._tstr_buf,16);\r
355         NyLPC_cMiMicDbCompiler_initialize(&header._binparser);\r
356         NyLPC_cMiMicTxtCompiler_initialize(&header._txtcmp);\r
357 \r
358         NyLPC_cHttpBasicHeaderParser_initialize(&parser,&handler);\r
359 \r
360         //プリフェッチしたデータを流す\r
361         NyLPC_cHttpBasicHeaderParser_parseInit(&parser,&(header.super));\r
362         NyLPC_cHttpdConnection_pushPrefetchInfo(i_connection,&parser,&header.super);\r
363         //後続をストリームから取り込む\r
364         if(!NyLPC_cHttpBasicHeaderParser_parseStream(&parser,NyLPC_cHttpdConnection_refStream(i_connection),&(header.super))){\r
365                 NyLPC_OnErrorGoto(Error2);\r
366         }\r
367         if(!NyLPC_cHttpBasicHeaderParser_parseFinish(&parser,&(header.super))){\r
368                 NyLPC_OnErrorGoto(Error2);\r
369         }\r
370         //Connection Modeの設定 1.1 && !closeの場合はCONTINUE\r
371         if(header.super.connection!=NyLPC_THttpMessgeHeader_Connection_CLOSE && header.super.startline.req.version==NyLPC_THttpVersion_11)\r
372         {\r
373                 NyLPC_cHttpdConnection_setConnectionMode(i_connection,NyLPC_TcHttpdConnection_CONNECTION_MODE_CONTINUE);\r
374         }\r
375         //CGIの実行\r
376         switch(header._content_id)\r
377         {\r
378         case CONTENT_ID_MVM:\r
379                 mvm(i_connection,&header);\r
380                 break;\r
381         default:\r
382                 NyLPC_OnErrorGoto(Error2);\r
383         }\r
384         NyLPC_cStr_finalize(&header._tstr);\r
385         NyLPC_cMiMicDbCompiler_finalize(&header._binparser);\r
386         NyLPC_cMiMicTxtCompiler_finalize(&header._txtcmp);\r
387         NyLPC_cHttpBasicHeaderParser_finalize(&parser);\r
388 //占有解除\r
389         NyLPC_cHttpdConnection_unlock(i_connection);\r
390         return NyLPC_TBool_TRUE;\r
391 Error2:\r
392         NyLPC_cHttpdConnection_sendResponseHeader2(i_connection,500,"text/html",0,NULL);\r
393         NyLPC_cStr_finalize(&header._tstr);\r
394         NyLPC_cMiMicDbCompiler_finalize(&header._binparser);\r
395         NyLPC_cMiMicTxtCompiler_finalize(&header._txtcmp);\r
396         NyLPC_cHttpBasicHeaderParser_finalize(&parser);\r
397         //VM排他ロックの解除\r
398         NyLPC_cHttpdConnection_unlock(i_connection);\r
399 Error1:\r
400         return NyLPC_TBool_FALSE;\r
401 }\r
402 \r
403 \r
404 /**\r
405  * イベントハンドラを継承\r
406  */\r
407 struct TVmEventHandler\r
408 {\r
409         struct NyLPC_TcMiMicVM_TEvent super;\r
410         const struct TModMiMicRemoteMcuHeader* req;\r
411         NyLPC_TcHttpdConnection_t* connection;\r
412         NyLPC_TUInt16 db_pos;\r
413         /** ストリームへ出力したデータの数*/\r
414         NyLPC_TUInt16 st_len;\r
415 };\r
416 \r
417 /**\r
418  * ストリームハンドラ(put)\r
419  */\r
420 static NyLPC_TBool mvmputs_json(struct NyLPC_TcMiMicVM_TEvent* i_eh,NyLPC_TUInt32 i_val)\r
421 {\r
422         struct TVmEventHandler* eh=(struct TVmEventHandler*)i_eh;\r
423         if(eh->st_len>0){\r
424                 eh->st_len++;\r
425                 return NyLPC_cHttpdConnection_sendResponseBodyF(eh->connection,",%u",i_val);\r
426         }else{\r
427                 eh->st_len++;\r
428                 return NyLPC_cHttpdConnection_sendResponseBodyF(eh->connection,"%u",i_val);\r
429         }\r
430 }\r
431 \r
432 /**\r
433  * ストリームハンドラ(get)\r
434  */\r
435 static NyLPC_TBool mvmgets(struct NyLPC_TcMiMicVM_TEvent* i_eh,NyLPC_TUInt32* o_val)\r
436 {\r
437         struct TVmEventHandler* eh=(struct TVmEventHandler*)i_eh;\r
438         //読み出し済みDBサイズの確認\r
439         if(eh->req->content.mvm.vm_instruction.db_len<=eh->db_pos){\r
440                 //読めない\r
441                 return NyLPC_TBool_FALSE;\r
442         }\r
443         *o_val=eh->req->content.mvm.vm_instruction.db_part[eh->db_pos];\r
444         eh->db_pos++;\r
445         return NyLPC_TBool_TRUE;\r
446 }\r
447 /**\r
448  * ネイティブCALLハンドラ\r
449  */\r
450 static NyLPC_TUInt32 nativeCall(struct NyLPC_TcMiMicVM_TEvent* i_evh,NyLPC_TUInt32 i_id,NyLPC_TcMiMicVM_t* i_vm)\r
451 {\r
452         (void)i_evh;\r
453 //      NyLPC_TNativeFunction f=getNativeFunctionById(i_id);\r
454 //      if(f==NULL){\r
455 //              return NyLPC_cMiMicVM_RESULT_RUNTIME_NG_UNKNOWN_CALL;\r
456 //      }\r
457 //      return f(i_vm)?NyLPC_cMiMicVM_RESULT_OK:NyLPC_cMiMicVM_RESULT_RUNTIME_NG_CALL;\r
458         return NyLPC_cMiMicVM_RESULT_RUNTIME_NG_CALL;\r
459 }\r
460 \r
461 \r
462 static void mvmsleep(struct NyLPC_TcMiMicVM_TEvent* i_eh,NyLPC_TUInt32 i_sleep_in_msec)\r
463 {\r
464         (void)i_eh;\r
465         NyLPC_cThread_sleep(i_sleep_in_msec);\r
466 }\r
467 \r
468 \r
469 /**\r
470  * MimicVMの起動と,ResponseJSONの起動\r
471  * @return\r
472  * 持続性接続を継続するかの真偽値\r
473  */\r
474 static void mvm(NyLPC_TcHttpdConnection_t* i_connection,const struct TModMiMicRemoteMcuHeader* i_rqh)\r
475 {\r
476         struct TVmEventHandler he;\r
477         NyLPC_TcMiMicVM_t vm;\r
478         NyLPC_TUInt32 vmret;\r
479         if(i_rqh->content.mvm.v!=QVAL_V_1 || i_rqh->content.mvm.o!=QVAL_O_JSON)\r
480         {\r
481                 NyLPC_cHttpdConnection_sendResponseHeader2(i_connection,500,"text/html",0,NULL);\r
482                 return;\r
483         }\r
484 \r
485         //Bodyを書く\r
486 //ここでリクエストパーサのエラー原因を調べて、詳細JSONをかくのもあり\r
487         //ハンドラインスタンスの設定\r
488         if(!NyLPC_cHttpdModUtils_sendJsonHeader(i_connection)){\r
489                 NyLPC_OnErrorGoto(Error1);\r
490         }\r
491 \r
492         he.super.get_stream=mvmgets;\r
493         he.super.put_stream=mvmputs_json;\r
494         he.super.native_call=nativeCall;\r
495         he.super.sleep=mvmsleep;\r
496         he.db_pos=0;\r
497         he.st_len=0;\r
498         he.connection=i_connection;\r
499         he.req=i_rqh;\r
500 \r
501         //起動VMの初期化\r
502         NyLPC_cMiMicVM_initialize(&vm,(struct NyLPC_TcMiMicVM_TEvent*)&(he.super));\r
503 \r
504         //JSONを書く。\r
505         if(!NyLPC_cHttpdConnection_sendResponseBodyF(i_connection,"{\"version\":\""MVM_VERSION"\",\"stream\":[")){\r
506                 NyLPC_OnErrorGoto(Error3);\r
507         }\r
508         //VMの実行\r
509         vmret=NyLPC_cMiMicVM_run(&(vm),i_rqh->content.mvm.vm_instruction.bc_buf,i_rqh->content.mvm.vm_instruction.txt_len);\r
510         if(!NyLPC_cHttpdConnection_sendResponseBodyF(i_connection,"],\"result\":%u}",vmret)){\r
511                 NyLPC_OnErrorGoto(Error3);\r
512         }\r
513         NyLPC_cMiMicVM_finalize(&vm);\r
514 \r
515         return;\r
516 Error3:\r
517         NyLPC_cMiMicVM_finalize(&vm);\r
518 Error1:\r
519         //VM排他ロックの解除\r
520         NyLPC_cMiMicVM_finalize(&vm);\r
521         NyLPC_cHttpBodyWriter_finalize(&hw);\r
522         return;\r
523 }\r
524 \r