icstruct.erl
来自「OTP是开放电信平台的简称」· ERL 代码 · 共 1,915 行 · 第 1/4 页
ERL
1,915 行
emit(Fd, " int oe_type = 0;\n",[]), emit(Fd, " int oe_array_size = 0;\n",[]), {ok, RamFd} = ram_file:open([], [binary, write]), emit_sizecount(array, G, N, nil, RamFd, {Name, Dim}, Type), ic_cbe:emit_tmp_variables(Fd), ic_codegen:nl(Fd), %% Move data from ram file to output file. {ok, Data} = ram_file:get_file(RamFd), emit(Fd, Data), ram_file:close(RamFd), emit(Fd, " return 0;\n\n",[]), emit(Fd, "}\n",[]), put(op_variable_count, 0), put(tmp_declarations, []), RefStr = get_refStr(Dim), case TypeDefFlag of typedef -> emit(HFd, "int ~s~s(CORBA_Environment *oe_env, ~s);\n", [ic_util:mk_oe_name(G, "encode_"), Name, Name]), emit(Fd, "int ~s~s(CORBA_Environment *oe_env, ~s oe_rec) {\n", [ic_util:mk_oe_name(G, "encode_"), Name, Name]); no_typedef -> emit(HFd, "int ~s~s(CORBA_Environment *oe_env, ~s oe_rec~s);\n", [ic_util:mk_oe_name(G, "encode_"), Name, ic_cbe:mk_c_type(G, N, Type), RefStr]), emit(Fd, "int ~s~s(CORBA_Environment *oe_env, ~s oe_rec~s) {\n", [ic_util:mk_oe_name(G, "encode_"), Name, ic_cbe:mk_c_type(G, N, Type), RefStr]) end, emit(Fd, " int oe_error_code = 0;\n",[]), {ok, RamFd1} = ram_file:open([], [binary, write]), case TypeDefFlag of typedef -> emit_encode(array, G, N, nil, RamFd1, {Name, Dim}, Type); no_typedef -> emit_encode(array_no_typedef, G, N, nil, RamFd1, {Name, Dim}, Type) end, ic_cbe:emit_tmp_variables(Fd), ic_codegen:nl(Fd), %% Move data from ram file to output file. {ok, Data1} = ram_file:get_file(RamFd1), emit(Fd, Data1), ram_file:close(RamFd1), emit(Fd, " return 0;\n\n",[]), emit(Fd, "}\n",[]), put(op_variable_count, 0), put(tmp_declarations, []), case TypeDefFlag of typedef -> emit(HFd, "int ~s~s(CORBA_Environment *oe_env, char *, " "int*, ~s);\n", [ic_util:mk_oe_name(G, "decode_"), Name, Name]), emit(Fd, "int ~s~s(CORBA_Environment *oe_env, char *oe_first, " "int* oe_outindex, ~s oe_out) {\n", [ic_util:mk_oe_name(G, "decode_"), Name, Name]); no_typedef -> emit(HFd, "int ~s~s(CORBA_Environment *oe_env, char *, int*, " "~s oe_rec~s);\n", [ic_util:mk_oe_name(G, "decode_"), Name, ic_cbe:mk_c_type(G, N, Type), RefStr]), emit(Fd, "int ~s~s(CORBA_Environment *oe_env, char *oe_first, " "int* oe_outindex, ~s oe_out~s) {\n", [ic_util:mk_oe_name(G, "decode_"), Name, ic_cbe:mk_c_type(G, N, Type), RefStr]) end, emit(Fd, " int oe_error_code = 0;\n",[]), emit(Fd, " int oe_array_size = 0;\n",[]), {ok, RamFd2} = ram_file:open([], [binary, write]), case TypeDefFlag of typedef -> emit_decode(array, G, N, nil, RamFd2, {Name, Dim}, Type); no_typedef -> emit_decode(array_no_typedef, G, N, nil, RamFd2, {Name, Dim}, Type) end, ic_cbe:emit_tmp_variables(Fd), ic_codegen:nl(Fd), %% Move data from ram file to output file. {ok, Data2} = ram_file:get_file(RamFd2), emit(Fd, Data2), ram_file:close(RamFd2), emit(Fd, " *oe_outindex = ~s;\n\n",[align("*oe_outindex")]), emit(Fd, " return 0;\n\n",[]), emit(Fd, "}\n",[]), file:close(Fd).get_refStr([]) -> "";get_refStr([X|Xs]) -> "[" ++ X ++ "]" ++ get_refStr(Xs).emit_sequence_head_def(G, N, X, T, c) -> %% T is the sequence case ic_genobj:is_hrlfile_open(G) of true -> Fd = ic_genobj:hrlfiled(G), SeqName = ic_util:to_undersc([ic_forms:get_id2(X) | N]), emit(Fd, "\n#ifndef __~s__\n",[ic_util:to_uppercase(SeqName)]), emit(Fd, "#define __~s__\n",[ic_util:to_uppercase(SeqName)]), ic_codegen:mcomment_light(Fd, [io_lib:format("Struct definition: ~s", [SeqName])], c), emit(Fd, "typedef struct {\n"), emit(Fd, " CORBA_unsigned_long _maximum;\n"), emit(Fd, " CORBA_unsigned_long _length;\n"), emit_seq_buffer(Fd, G, N, T#sequence.type), emit(Fd, "} ~s;\n\n", [SeqName]), create_c_struct_coding_file(G, N, X, T, SeqName, T#sequence.type, sequence_head), emit(Fd, "\n#endif\n\n"); false -> ok end.emit_seq_buffer(Fd, G, N, Type) -> emit(Fd, " ~s* _buffer;\n", [ic_cbe:mk_c_type(G, N, Type)]).%%------------------------------------------------------------%%%% Emit decode bodies for functions in C for array, sequences and%% structs.%%%%------------------------------------------------------------emit_decode(array, G, N, _T, Fd, {_Name, Dim}, Type) -> emit(Fd, " if((char*) oe_out == oe_first)\n",[]), AlignName = lists:concat(["*oe_outindex + ", dim_multiplication(Dim), " * sizeof(", ic_cbe:mk_c_type(G, N, Type),")"]), emit(Fd, " *oe_outindex = ~s;\n\n",[align(AlignName)]), array_decode_dimension_loop(G, N, Fd, Dim, "", Type, array);emit_decode(array_no_typedef, G, N, _T, Fd, {_Name, Dim}, Type) -> emit(Fd, " if((char*) oe_out == oe_first)\n",[]), AlignName = lists:concat(["*oe_outindex + ", dim_multiplication(Dim), " * sizeof(", ic_cbe:mk_c_type(G, N, Type),")"]), emit(Fd, " *oe_outindex = ~s;\n\n",[align(AlignName)]), array_decode_dimension_loop(G, N, Fd, Dim, "", Type, array_no_typedef);emit_decode(sequence_head, G, N, T, Fd, SeqName, ElType) -> ic_cbe:store_tmp_decl(" int oe_seq_len = 0;\n", []), ic_cbe:store_tmp_decl(" int oe_seq_count = 0;\n", []), ic_cbe:store_tmp_decl(" int oe_seq_dummy = 0;\n", []), TmpBuf = case ictype:isBasicTypeOrEterm(G, N, ElType) of true -> Tmp = "oe_seq_tmpbuf", ic_cbe:store_tmp_decl(" char* ~s = 0;\n", [Tmp]), Tmp; false -> "NOT USED" end, MaxSize = get_seq_max(T), emit(Fd, " if((char*) oe_out == oe_first)\n",[]), emit(Fd, " *oe_outindex = ~s;\n\n", [align(["*oe_outindex + sizeof(", SeqName, ")"])]), Ctype = ic_cbe:mk_c_type(G, N, ElType), emit(Fd, " if ((oe_error_code = ei_decode_list_header(oe_env->_inbuf, " "&oe_env->_iin, &oe_seq_len)) < 0) {\n"), case ictype:isBasicTypeOrEterm(G, N, ElType) of true -> emit(Fd, " int oe_type = 0;\n"), emit(Fd, " (int) ei_get_type(oe_env->_inbuf, &oe_env->_iin, " "&oe_type, &oe_seq_len);\n\n"), if MaxSize == infinity -> ok; true -> emit(Fd, " if (oe_seq_len > ~w) {\n", [MaxSize]), emit(Fd, " CORBA_exc_set(oe_env, " "CORBA_SYSTEM_EXCEPTION, DATA_CONVERSION, " "\"Length of sequence `~s' out of bound\");\n" " return -1;\n }\n", [SeqName]) end, emit(Fd, " oe_out->_maximum = oe_seq_len;\n"), emit(Fd, " oe_out->_length = oe_seq_len;\n"), emit(Fd, " oe_out->_buffer = (void *) (oe_first + " "*oe_outindex);\n"), emit(Fd, " *oe_outindex = ~s;\n", [align(["*oe_outindex + (sizeof(", Ctype, ") * " "oe_out->_length)"])]), emit(Fd, " if ((~s = malloc(oe_seq_len + 1)) == NULL) {\n" " CORBA_exc_set(oe_env, CORBA_SYSTEM_EXCEPTION, " "NO_MEMORY, \"Cannot malloc\");\n" " return -1;\n" " }\n", [TmpBuf]), emit(Fd, " if ((oe_error_code = ei_decode_string(" "oe_env->_inbuf, &oe_env->_iin, ~s)) < 0) {\n", [TmpBuf]), emit(Fd, " CORBA_free(~s);\n\n", [TmpBuf]), emit_c_dec_rpt(Fd, " ", "string1", []), emit(Fd, " return oe_error_code;\n }\n"), emit(Fd, " for (oe_seq_count = 0; " "oe_seq_count < oe_out->_length; oe_seq_count++)\n"), case ictype:isBasicType(G, N, ElType) of true -> emit(Fd, " oe_out->_buffer[oe_seq_count] = (unsigned char) " "~s[oe_seq_count];\n\n", [TmpBuf]); false -> %% Term emit(Fd, " oe_out->_buffer[oe_seq_count] = " "erl_mk_int(~s[oe_seq_count]);\n\n",[TmpBuf]) % XXXX What? end, emit(Fd, " CORBA_free(~s);\n\n", [TmpBuf]); false -> emit(Fd, " return oe_error_code;\n") end, emit(Fd, " } else {\n"), if MaxSize == infinity -> ok; true -> emit(Fd, " if (oe_seq_len > ~w) {\n", [MaxSize]), emit(Fd, " CORBA_exc_set(oe_env, " "CORBA_SYSTEM_EXCEPTION, DATA_CONVERSION, " "\"Length of sequence `~s' out of bound\");\n" " return -1;\n }\n", [SeqName]) end, emit(Fd, " oe_out->_maximum = oe_seq_len;\n"), emit(Fd, " oe_out->_length = oe_seq_len;\n"), emit(Fd, " oe_out->_buffer = (void *) (oe_first + *oe_outindex);\n"), emit(Fd, " *oe_outindex = ~s;\n\n", [align(["*oe_outindex + (sizeof(", Ctype, ") * oe_out->_length)"])]), if Ctype == "CORBA_char *" -> emit(Fd, " for (oe_seq_count = 0; " "oe_seq_count < oe_out->_length; oe_seq_count++) {\n"), emit(Fd, " oe_out->_buffer[oe_seq_count] = " "(void*) (oe_first + *oe_outindex);\n\n"), ic_cbe:emit_decoding_stmt(G, N, Fd, ElType, "oe_out->_buffer[oe_seq_count]", "", "oe_env->_inbuf", 0, "", caller_dyn), emit(Fd, " *oe_outindex = ~s;", [align(["*oe_outindex + strlen(oe_out->_buffer[" "oe_seq_count]) + 1"])]); true -> emit(Fd, " for (oe_seq_count = 0; " "oe_seq_count < oe_out->_length; oe_seq_count++) {\n"), case ictype:isArray(G, N, ElType) of %% XXX Silly. There is no real difference between the %% C statements produced by the following calls. true -> ic_cbe:emit_decoding_stmt(G, N, Fd, ElType, "oe_out->_buffer[oe_seq_count]", "", "oe_env->_inbuf", 0, "oe_outindex", generator); false -> ic_cbe:emit_decoding_stmt(G, N, Fd, ElType, "oe_out->_buffer + oe_seq_count", "", "oe_env->_inbuf", 0, "oe_outindex", generator) end end, emit(Fd, " }\n"), emit(Fd, " if (oe_out->_length != 0) {\n"), emit(Fd, " if ((oe_error_code = ei_decode_list_header(" "oe_env->_inbuf, &oe_env->_iin, &oe_seq_dummy)) < 0) {\n"), emit_c_dec_rpt(Fd, " ", "ei_decode_list_header", []), emit(Fd, " return oe_error_code;\n }\n"), emit(Fd, " } else\n"), emit(Fd, " oe_out->_buffer = NULL;\n"), emit(Fd, " }\n");emit_decode(struct, G, N, _T, Fd, StructName, ElTypes) -> Length = length(ElTypes) + 1, Tname = ic_cbe:mk_variable_name(op_variable_count), Tname1 = ic_cbe:mk_variable_name(op_variable_count), ic_cbe:store_tmp_decl(" int ~s = 0;\n",[Tname]), ic_cbe:store_tmp_decl(" char ~s[256];\n\n",[Tname1]), emit(Fd, " if((char*) oe_out == oe_first)\n",[]), AlignName = lists:concat(["*oe_outindex + sizeof(",StructName,")"]), emit(Fd, " *oe_outindex = ~s;\n\n", [align(AlignName)]), emit(Fd, " if ((oe_error_code = ei_decode_tuple_header(oe_env->_inbuf, " "&oe_env->_iin, &~s)) < 0) {\n", [Tname]), emit_c_dec_rpt(Fd, " ", "ei_decode_tuple_header", []), emit(Fd, " return oe_error_code;\n }\n"), emit(Fd, " if (~s != ~p) {\n",[Tname, Length]), emit_c_dec_rpt(Fd, " ", "tuple header size != ~p", [Length]), emit(Fd, " return -1;\n }\n"), emit(Fd, " if ((oe_error_code = ei_decode_atom(oe_env->_inbuf, " "&oe_env->_iin, ~s)) < 0) {\n", [Tname1]), emit_c_dec_rpt(Fd, " ", "ei_decode_atom", []), emit(Fd, " return oe_error_code;\n }\n"), emit(Fd, " if (strcmp(~s, ~p) != 0)\n",[Tname1, StructName]), emit(Fd, " return -1;\n\n"), lists:foreach( fun({ET, EN}) -> case ic_cbe:is_variable_size(G, N, ET) of true -> case ET of {struct, _, _, _} -> %% Sequence member = a struct ic_cbe:emit_decoding_stmt(G, N, Fd, StructName ++ "_" ++ ic_forms:get_id2(ET), "&oe_out->" ++ EN, "", "oe_env->_inbuf", 0, "oe_outindex", generator); {sequence, _, _} -> %% Sequence member = a struct XXX ?? ic_cbe:emit_decoding_stmt(G, N, Fd, StructName ++ "_" ++ EN, "&oe_out->" ++ EN, "", "oe_env->_inbuf", 0, "oe_outindex", generator); {_,{array, _, _}} -> emit(Fd, " oe_out->~s = (void *) " "(oe_first+*oe_outindex);\n\n",[EN]), ic_cbe:emit_decoding_stmt(G, N, Fd, StructName ++ "_" ++ EN, "oe_out->" ++ EN , "", "oe_env->_inbuf", 0, "oe_outindex", generator); {union, _, _, _, _} -> %% Sequence member = a union ic_cbe:emit_decoding_stmt(G, N, Fd, StructName ++ "_" ++ ic_forms:get_id2(ET), "&oe_out->" ++ EN, "", "oe_env->_inbuf", 0, "oe_outindex", generator); {string,_} -> ic_cbe:emit_decoding_stmt(G, N, Fd, ET, "oe_out->" ++ EN , "", "oe_env->_inbuf", 0, "oe_outindex", generator_malloc); {scoped_id,_,_,_} -> case ictype:member2type(G,StructName,EN) of array -> ic_cbe:emit_decoding_stmt(G, N, Fd, ET, "oe_out->" ++ EN, "", "oe_env->" "_inbuf", 0, "oe_outindex", generator); struct -> ic_cbe:emit_decoding_stmt(G, N, Fd, ET, "&oe_out->" ++ EN , "", "oe_env->" "_inbuf", 0, "oe_outindex", generator); sequence -> ic_cbe:emit_decoding_stmt(G, N, Fd, ET, "&oe_out->" ++ EN, "", "oe_env->" "_inbuf", 0, "oe_outindex", generator); union -> ic_cbe:emit_decoding_stmt(G, N, Fd, ET, "&oe_out->" ++ EN, "", "oe_env->" "_inbuf", 0, "oe_outindex", generator); _ -> ic_cbe:emit_decoding_stmt(G, N, Fd, ET, "oe_out->" ++ EN, "", "oe_env->" "_inbuf", 0, "oe_outindex", generator) end; _ -> emit(Fd, " oe_out->~s = (void *) " "(oe_first+*oe_outindex);\n\n",[EN]), ic_cbe:emit_decoding_stmt(G, N, Fd, ET, "oe_out->" ++ EN , "", "oe_env->_inbuf", 0, "oe_outindex", generator) end; false -> case ET of {struct, _, _, _} -> %% A struct member ic_cbe:emit_decoding_stmt(G, N, Fd, StructName ++ "_" ++ ic_forms:get_id2(ET), "&oe_out->" ++ EN , "", "oe_env->_inbuf",
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?