openubmc-bingo 0.5.240__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of openubmc-bingo might be problematic. Click here for more details.

Files changed (242) hide show
  1. bmcgo/__init__.py +12 -0
  2. bmcgo/bmcgo.py +22 -0
  3. bmcgo/bmcgo_config.py +176 -0
  4. bmcgo/cli/__init__.py +10 -0
  5. bmcgo/cli/cli.py +584 -0
  6. bmcgo/codegen/__init__.py +14 -0
  7. bmcgo/codegen/c/__init__.py +9 -0
  8. bmcgo/codegen/c/annotation.py +52 -0
  9. bmcgo/codegen/c/argument.py +42 -0
  10. bmcgo/codegen/c/codegen.py +153 -0
  11. bmcgo/codegen/c/comment.py +22 -0
  12. bmcgo/codegen/c/ctype_defination.py +353 -0
  13. bmcgo/codegen/c/helper.py +87 -0
  14. bmcgo/codegen/c/interface.py +63 -0
  15. bmcgo/codegen/c/method.py +82 -0
  16. bmcgo/codegen/c/property.py +180 -0
  17. bmcgo/codegen/c/renderer.py +21 -0
  18. bmcgo/codegen/c/signal.py +64 -0
  19. bmcgo/codegen/c/template/client.c.mako +145 -0
  20. bmcgo/codegen/c/template/client.h.mako +36 -0
  21. bmcgo/codegen/c/template/interface.c.mako +0 -0
  22. bmcgo/codegen/c/template/interface.introspect.xml.mako +99 -0
  23. bmcgo/codegen/c/template/micro_component.c.mako +32 -0
  24. bmcgo/codegen/c/template/public.c.mako +228 -0
  25. bmcgo/codegen/c/template/public.h.mako +128 -0
  26. bmcgo/codegen/c/template/server.c.mako +104 -0
  27. bmcgo/codegen/c/template/server.h.mako +36 -0
  28. bmcgo/codegen/lua/.lua-format +7 -0
  29. bmcgo/codegen/lua/Makefile +101 -0
  30. bmcgo/codegen/lua/__init__.py +9 -0
  31. bmcgo/codegen/lua/codegen.py +171 -0
  32. bmcgo/codegen/lua/proto/Makefile +87 -0
  33. bmcgo/codegen/lua/proto/ipmi_types.proto +17 -0
  34. bmcgo/codegen/lua/proto/types.proto +52 -0
  35. bmcgo/codegen/lua/script/check_intfs.py +161 -0
  36. bmcgo/codegen/lua/script/dto/__init__.py +11 -0
  37. bmcgo/codegen/lua/script/dto/exception.py +53 -0
  38. bmcgo/codegen/lua/script/dto/kepler_abstract.py +47 -0
  39. bmcgo/codegen/lua/script/dto/options.py +33 -0
  40. bmcgo/codegen/lua/script/dto/print_simple.py +19 -0
  41. bmcgo/codegen/lua/script/dto/redfish_api.py +241 -0
  42. bmcgo/codegen/lua/script/dto/url_route.py +195 -0
  43. bmcgo/codegen/lua/script/gen_db_json.py +444 -0
  44. bmcgo/codegen/lua/script/gen_depends.py +89 -0
  45. bmcgo/codegen/lua/script/gen_entry.py +263 -0
  46. bmcgo/codegen/lua/script/gen_feature_json.py +156 -0
  47. bmcgo/codegen/lua/script/gen_historical_local_db_json.py +88 -0
  48. bmcgo/codegen/lua/script/gen_intf_json.py +261 -0
  49. bmcgo/codegen/lua/script/gen_intf_rpc_json.py +575 -0
  50. bmcgo/codegen/lua/script/gen_ipmi_json.py +485 -0
  51. bmcgo/codegen/lua/script/gen_mdb_json.py +117 -0
  52. bmcgo/codegen/lua/script/gen_rpc_msg_json.py +487 -0
  53. bmcgo/codegen/lua/script/gen_schema.py +302 -0
  54. bmcgo/codegen/lua/script/ipmi_types_pb2.py +135 -0
  55. bmcgo/codegen/lua/script/loader/__init__.py +11 -0
  56. bmcgo/codegen/lua/script/loader/file_utils.py +33 -0
  57. bmcgo/codegen/lua/script/loader/kepler_abstract_collect.py +79 -0
  58. bmcgo/codegen/lua/script/loader/kepler_abstract_loader.py +47 -0
  59. bmcgo/codegen/lua/script/loader/redfish_loader.py +127 -0
  60. bmcgo/codegen/lua/script/lua_format.py +62 -0
  61. bmcgo/codegen/lua/script/mds_util.py +385 -0
  62. bmcgo/codegen/lua/script/merge_model.py +330 -0
  63. bmcgo/codegen/lua/script/merge_proto_algo.py +85 -0
  64. bmcgo/codegen/lua/script/proto_loader.py +47 -0
  65. bmcgo/codegen/lua/script/proto_plugin.py +140 -0
  66. bmcgo/codegen/lua/script/redfish_source_tree.py +118 -0
  67. bmcgo/codegen/lua/script/render_utils/__init__.py +38 -0
  68. bmcgo/codegen/lua/script/render_utils/base.py +25 -0
  69. bmcgo/codegen/lua/script/render_utils/client_lua.py +98 -0
  70. bmcgo/codegen/lua/script/render_utils/controller_lua.py +71 -0
  71. bmcgo/codegen/lua/script/render_utils/db_lua.py +224 -0
  72. bmcgo/codegen/lua/script/render_utils/error_lua.py +185 -0
  73. bmcgo/codegen/lua/script/render_utils/factory.py +52 -0
  74. bmcgo/codegen/lua/script/render_utils/ipmi_lua.py +159 -0
  75. bmcgo/codegen/lua/script/render_utils/ipmi_message_lua.py +24 -0
  76. bmcgo/codegen/lua/script/render_utils/mdb_lua.py +177 -0
  77. bmcgo/codegen/lua/script/render_utils/mdb_register.py +215 -0
  78. bmcgo/codegen/lua/script/render_utils/message_lua.py +26 -0
  79. bmcgo/codegen/lua/script/render_utils/messages_lua.py +156 -0
  80. bmcgo/codegen/lua/script/render_utils/model_lua.py +485 -0
  81. bmcgo/codegen/lua/script/render_utils/old_model_lua.py +429 -0
  82. bmcgo/codegen/lua/script/render_utils/plugin_lua.py +38 -0
  83. bmcgo/codegen/lua/script/render_utils/redfish_proto.py +86 -0
  84. bmcgo/codegen/lua/script/render_utils/request_lua.py +76 -0
  85. bmcgo/codegen/lua/script/render_utils/service_lua.py +130 -0
  86. bmcgo/codegen/lua/script/render_utils/utils_message_lua.py +125 -0
  87. bmcgo/codegen/lua/script/render_utils/validate_lua.py +221 -0
  88. bmcgo/codegen/lua/script/sep_ipmi_message_cmds.py +217 -0
  89. bmcgo/codegen/lua/script/template.py +166 -0
  90. bmcgo/codegen/lua/script/types_pb2.py +516 -0
  91. bmcgo/codegen/lua/script/utils.py +663 -0
  92. bmcgo/codegen/lua/script/validate.py +80 -0
  93. bmcgo/codegen/lua/script/yaml_to_json.py +73 -0
  94. bmcgo/codegen/lua/templates/Makefile +114 -0
  95. bmcgo/codegen/lua/templates/apps/Makefile +261 -0
  96. bmcgo/codegen/lua/templates/apps/Makefile.mdb.mk +64 -0
  97. bmcgo/codegen/lua/templates/apps/app.lua.mako +19 -0
  98. bmcgo/codegen/lua/templates/apps/class.lua.mako +35 -0
  99. bmcgo/codegen/lua/templates/apps/client.lua.mako +429 -0
  100. bmcgo/codegen/lua/templates/apps/controller.lua.mako +276 -0
  101. bmcgo/codegen/lua/templates/apps/datas.lua.mako +8 -0
  102. bmcgo/codegen/lua/templates/apps/db.lua.mako +89 -0
  103. bmcgo/codegen/lua/templates/apps/entry.lua.mako +128 -0
  104. bmcgo/codegen/lua/templates/apps/feature.lua.mako +37 -0
  105. bmcgo/codegen/lua/templates/apps/generate_route.mako +25 -0
  106. bmcgo/codegen/lua/templates/apps/impl_feature.lua.mako +72 -0
  107. bmcgo/codegen/lua/templates/apps/ipmi.lua.mako +97 -0
  108. bmcgo/codegen/lua/templates/apps/ipmi_cmd.lua.mako +18 -0
  109. bmcgo/codegen/lua/templates/apps/ipmi_message.lua.mako +36 -0
  110. bmcgo/codegen/lua/templates/apps/local_db.lua.mako +263 -0
  111. bmcgo/codegen/lua/templates/apps/main.lua.mako +25 -0
  112. bmcgo/codegen/lua/templates/apps/mc.lua.mako +77 -0
  113. bmcgo/codegen/lua/templates/apps/mdb.lua.mako +45 -0
  114. bmcgo/codegen/lua/templates/apps/mdb_interface.lua.mako +73 -0
  115. bmcgo/codegen/lua/templates/apps/message.lua.mako +38 -0
  116. bmcgo/codegen/lua/templates/apps/model.lua.mako +239 -0
  117. bmcgo/codegen/lua/templates/apps/orm_classes.lua.mako +16 -0
  118. bmcgo/codegen/lua/templates/apps/plugin.lua.mako +8 -0
  119. bmcgo/codegen/lua/templates/apps/redfish.proto.mako +47 -0
  120. bmcgo/codegen/lua/templates/apps/service.lua.mako +440 -0
  121. bmcgo/codegen/lua/templates/apps/signal_listen.lua.mako +19 -0
  122. bmcgo/codegen/lua/templates/apps/utils/default_intf.lua.mako +41 -0
  123. bmcgo/codegen/lua/templates/apps/utils/enum.mako +10 -0
  124. bmcgo/codegen/lua/templates/apps/utils/imports.mako +13 -0
  125. bmcgo/codegen/lua/templates/apps/utils/mdb_intf.lua.mako +25 -0
  126. bmcgo/codegen/lua/templates/apps/utils/mdb_obj.lua.mako +23 -0
  127. bmcgo/codegen/lua/templates/apps/utils/message.mako +160 -0
  128. bmcgo/codegen/lua/templates/apps/utils/request.lua.mako +59 -0
  129. bmcgo/codegen/lua/templates/apps/utils/validate.mako +83 -0
  130. bmcgo/codegen/lua/templates/errors.lua.mako +36 -0
  131. bmcgo/codegen/lua/templates/messages.lua.mako +32 -0
  132. bmcgo/codegen/lua/templates/new_app/.clang-format.mako +170 -0
  133. bmcgo/codegen/lua/templates/new_app/.gitignore.mako +26 -0
  134. bmcgo/codegen/lua/templates/new_app/CHANGELOG.md.mako +0 -0
  135. bmcgo/codegen/lua/templates/new_app/CMakeLists.txt.mako +29 -0
  136. bmcgo/codegen/lua/templates/new_app/Makefile.mako +25 -0
  137. bmcgo/codegen/lua/templates/new_app/README.md.mako +0 -0
  138. bmcgo/codegen/lua/templates/new_app/conanfile.py.mako +7 -0
  139. bmcgo/codegen/lua/templates/new_app/config.cfg.mako +6 -0
  140. bmcgo/codegen/lua/templates/new_app/mds/model.json.mako +3 -0
  141. bmcgo/codegen/lua/templates/new_app/mds/service.json.mako +21 -0
  142. bmcgo/codegen/lua/templates/new_app/permissions.ini.mako +16 -0
  143. bmcgo/codegen/lua/templates/new_app/src/lualib/${project_name}_app.lua.mako +16 -0
  144. bmcgo/codegen/lua/templates/new_app/src/service/main.lua.mako +25 -0
  145. bmcgo/codegen/lua/templates/new_app/test/integration/test_${project_name}.conf.mako +9 -0
  146. bmcgo/codegen/lua/templates/new_app/test/integration/test_${project_name}.lua.mako +47 -0
  147. bmcgo/codegen/lua/templates/new_app/test/unit/test.lua.mako +23 -0
  148. bmcgo/codegen/lua/templates/new_app/user_conf/rootfs/etc/systemd/system/${project_name}.service.mako +18 -0
  149. bmcgo/codegen/lua/templates/new_app/user_conf/rootfs/etc/systemd/system/multi-user.target.wants/${project_name}.service.link +1 -0
  150. bmcgo/component/__init__.py +10 -0
  151. bmcgo/component/analysis/analysis.py +183 -0
  152. bmcgo/component/analysis/build_deps.py +165 -0
  153. bmcgo/component/analysis/data_deps.py +333 -0
  154. bmcgo/component/analysis/dep-rules.json +912 -0
  155. bmcgo/component/analysis/dep_node.py +110 -0
  156. bmcgo/component/analysis/intf_deps.py +163 -0
  157. bmcgo/component/analysis/intf_validation.py +254 -0
  158. bmcgo/component/analysis/rule.py +211 -0
  159. bmcgo/component/analysis/smc_dfx_whitelist.json +11 -0
  160. bmcgo/component/analysis/sr_validation.py +391 -0
  161. bmcgo/component/build.py +222 -0
  162. bmcgo/component/component_dt_version_parse.py +348 -0
  163. bmcgo/component/component_helper.py +114 -0
  164. bmcgo/component/coverage/__init__.py +11 -0
  165. bmcgo/component/coverage/c_incremental_cov_report.template +53 -0
  166. bmcgo/component/coverage/incremental_cov.py +464 -0
  167. bmcgo/component/deploy.py +110 -0
  168. bmcgo/component/gen.py +169 -0
  169. bmcgo/component/package_info.py +236 -0
  170. bmcgo/component/template/conanbase.py.mako +278 -0
  171. bmcgo/component/template/conanfile.deploy.py.mako +40 -0
  172. bmcgo/component/test.py +947 -0
  173. bmcgo/errors.py +119 -0
  174. bmcgo/frame.py +217 -0
  175. bmcgo/functional/__init__.py +10 -0
  176. bmcgo/functional/analysis.py +96 -0
  177. bmcgo/functional/bmc_studio_action.py +98 -0
  178. bmcgo/functional/check.py +185 -0
  179. bmcgo/functional/conan_index_build.py +251 -0
  180. bmcgo/functional/config.py +332 -0
  181. bmcgo/functional/csr_build.py +724 -0
  182. bmcgo/functional/deploy.py +263 -0
  183. bmcgo/functional/diff.py +235 -0
  184. bmcgo/functional/fetch.py +235 -0
  185. bmcgo/functional/full_component.py +391 -0
  186. bmcgo/functional/maintain.py +381 -0
  187. bmcgo/functional/new.py +166 -0
  188. bmcgo/functional/schema_valid.py +111 -0
  189. bmcgo/functional/simple_sign.py +104 -0
  190. bmcgo/functional/upgrade.py +78 -0
  191. bmcgo/ipmigen/__init__.py +13 -0
  192. bmcgo/ipmigen/ctype_defination.py +82 -0
  193. bmcgo/ipmigen/ipmigen.py +309 -0
  194. bmcgo/ipmigen/template/cmd.c.mako +366 -0
  195. bmcgo/ipmigen/template/ipmi.c.mako +25 -0
  196. bmcgo/ipmigen/template/ipmi.h.mako +51 -0
  197. bmcgo/logger.py +176 -0
  198. bmcgo/misc.py +117 -0
  199. bmcgo/target/app.yml +17 -0
  200. bmcgo/target/install_sdk.yml +15 -0
  201. bmcgo/target/personal.yml +53 -0
  202. bmcgo/target/publish.yml +45 -0
  203. bmcgo/tasks/__init__.py +11 -0
  204. bmcgo/tasks/download_buildtools_hm.py +124 -0
  205. bmcgo/tasks/misc.py +15 -0
  206. bmcgo/tasks/task.py +354 -0
  207. bmcgo/tasks/task_build_conan.py +714 -0
  208. bmcgo/tasks/task_build_rootfs_img.py +595 -0
  209. bmcgo/tasks/task_buildgppbin.py +88 -0
  210. bmcgo/tasks/task_buildhpm_ext4.py +82 -0
  211. bmcgo/tasks/task_create_interface_config.py +122 -0
  212. bmcgo/tasks/task_download_buildtools.py +99 -0
  213. bmcgo/tasks/task_download_dependency.py +72 -0
  214. bmcgo/tasks/task_hpm_envir_prepare.py +112 -0
  215. bmcgo/tasks/task_packet_to_supporte.py +87 -0
  216. bmcgo/tasks/task_prepare.py +105 -0
  217. bmcgo/tasks/task_sign_and_pack_hpm.py +42 -0
  218. bmcgo/utils/__init__.py +10 -0
  219. bmcgo/utils/buffer.py +128 -0
  220. bmcgo/utils/combine_json_schemas.py +170 -0
  221. bmcgo/utils/component_post.py +54 -0
  222. bmcgo/utils/component_version_check.py +86 -0
  223. bmcgo/utils/config.py +1067 -0
  224. bmcgo/utils/fetch_component_code.py +232 -0
  225. bmcgo/utils/install_manager.py +61 -0
  226. bmcgo/utils/installations/__init__.py +10 -0
  227. bmcgo/utils/installations/base_installer.py +70 -0
  228. bmcgo/utils/installations/install_consts.py +30 -0
  229. bmcgo/utils/installations/install_plans/bingo.yml +11 -0
  230. bmcgo/utils/installations/install_workflow.py +50 -0
  231. bmcgo/utils/installations/installers/apt_installer.py +177 -0
  232. bmcgo/utils/installations/installers/pip_installer.py +46 -0
  233. bmcgo/utils/installations/version_util.py +100 -0
  234. bmcgo/utils/mapping_config_patch.py +443 -0
  235. bmcgo/utils/perf_analysis.py +114 -0
  236. bmcgo/utils/tools.py +704 -0
  237. bmcgo/worker.py +417 -0
  238. openubmc_bingo-0.5.240.dist-info/METADATA +30 -0
  239. openubmc_bingo-0.5.240.dist-info/RECORD +242 -0
  240. openubmc_bingo-0.5.240.dist-info/WHEEL +5 -0
  241. openubmc_bingo-0.5.240.dist-info/entry_points.txt +2 -0
  242. openubmc_bingo-0.5.240.dist-info/top_level.txt +1 -0
@@ -0,0 +1,330 @@
1
+ #!/usr/bin/env python3
2
+ # coding=utf-8
3
+ # Copyright (c) 2024 Huawei Technologies Co., Ltd.
4
+ # openUBMC is licensed under Mulan PSL v2.
5
+ # You can use this software according to the terms and conditions of the Mulan PSL v2.
6
+ # You may obtain a copy of Mulan PSL v2 at:
7
+ # http://license.coscl.org.cn/MulanPSL2
8
+ # THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
9
+ # EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
10
+ # MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
11
+ # See the Mulan PSL v2 for more details.
12
+
13
+ import json
14
+ import logging
15
+ import getopt
16
+ import sys
17
+ import os
18
+ import stat
19
+ from collections import OrderedDict
20
+ import mds_util as utils
21
+ from utils import Utils
22
+ from bmcgo.utils.tools import Tools
23
+
24
+
25
+ tool = Tools()
26
+ log = tool.log
27
+ OPTIONS_SETTING = ["explicit", "volatile"]
28
+ CHECK_PROPS_SETTINGS = ["usage", "alias", "primaryKey", "uniqueKey", "privilege", "default", "featureTag", "critical",
29
+ "notAllowNull", "refInterface", "displayDescription", "sensitive"]
30
+
31
+
32
+ def save_file(of_name, model_new):
33
+ if os.path.exists(of_name):
34
+ with os.fdopen(os.open(of_name, os.O_RDONLY, stat.S_IRUSR), "r") as load_f:
35
+ if json.load(load_f) == model_new:
36
+ logging.info("schema 未发生更改")
37
+ return
38
+
39
+ with os.fdopen(
40
+ os.open(
41
+ of_name, os.O_WRONLY | os.O_CREAT | os.O_TRUNC, stat.S_IWUSR | stat.S_IRUSR
42
+ ),
43
+ "w",
44
+ ) as load_f:
45
+ json.dump(model_new, load_f, indent=4)
46
+ logging.info("schema 已经更改")
47
+
48
+
49
+ def fill_req_optional(intf_info, prop, properties, prop_data):
50
+ if "req" not in properties[prop] or "req" not in prop_data:
51
+ return
52
+
53
+ class_name, intf_name = intf_info["class_name"], intf_info["intf_name"]
54
+ has_optional = False
55
+ for req_param, req_param_data in prop_data["req"].items():
56
+ op = properties[prop]["req"].get(req_param, {}).get('optional', False)
57
+ if not op:
58
+ if has_optional:
59
+ raise RuntimeError(f"model.json中{class_name}类{intf_name}接口的{prop}方法不满足所有可选参数在入参列表的末尾")
60
+ continue
61
+
62
+ has_optional = True
63
+ default = properties[prop]["req"].get(req_param, {}).get('default')
64
+ if default is None:
65
+ raise RuntimeError(f"model.json中{class_name}类{intf_name}接口的{prop}方法的可选入参{req_param}未配置default字段")
66
+ req_param_data["optional"] = op
67
+ req_param_data["default"] = default
68
+
69
+
70
+ def fill_req_displaydescription(intf_info, prop, properties, prop_data):
71
+ if "req" not in properties[prop] or "req" not in prop_data:
72
+ return
73
+
74
+ class_name, intf_name = intf_info["class_name"], intf_info["intf_name"]
75
+ for req_param, req_param_data in prop_data["req"].items():
76
+ display_des = properties[prop]["req"].get(req_param, {}).get('displayDescription', False)
77
+ if not display_des:
78
+ continue
79
+
80
+ req_param_data["displayDescription"] = display_des
81
+
82
+
83
+ def get_options_from_mds(prop, properties, prop_data):
84
+ if "options" not in properties[prop]:
85
+ return
86
+ for option in OPTIONS_SETTING:
87
+ if option in properties[prop]["options"]:
88
+ prop_data["options"] = prop_data.get("options", {})
89
+ prop_data["options"][option] = properties[prop]["options"].get(option)
90
+
91
+
92
+ def merge_props_and_data(intf_info, prop, properties, prop_data, check_props):
93
+ if prop not in properties:
94
+ properties[prop] = {}
95
+ else:
96
+ if Utils.get_lua_codegen_version() >= 16:
97
+ fill_req_optional(intf_info, prop, properties, prop_data)
98
+ fill_req_displaydescription(intf_info, prop, properties, prop_data)
99
+
100
+ if Utils.get_lua_codegen_version() >= 18:
101
+ get_options_from_mds(prop, properties, prop_data)
102
+
103
+ for check_prop in check_props:
104
+ if properties[prop].get(check_prop, False):
105
+ prop_data[check_prop] = properties[prop].get(check_prop)
106
+ properties[prop] = prop_data
107
+
108
+
109
+ def merge_when_intf_exist(model, intf, item, class_name, intf_name):
110
+ check_props = CHECK_PROPS_SETTINGS
111
+
112
+ if Utils.get_lua_codegen_version() >= 16:
113
+ check_props.append("cmdName")
114
+ check_props.append("displayDescription")
115
+
116
+ if item not in intf:
117
+ if item in model:
118
+ model.pop(item)
119
+ return
120
+
121
+ if item not in model:
122
+ model[item] = {}
123
+
124
+ properties = model[item]
125
+ for prop in list(properties):
126
+ if prop in intf[item]:
127
+ continue
128
+ label = "方法" if item == "methods" else "信号"
129
+ raise RuntimeError(f"model.json中类{class_name}接口{intf_name}的{label}{prop}在mdb_interface中没有被定义")
130
+
131
+ intf_info = {"class_name": class_name, "intf_name": intf_name}
132
+ for prop, prop_data in intf[item].items():
133
+ merge_props_and_data(intf_info, prop, properties, prop_data, check_props)
134
+
135
+
136
+ def copy_when_exist(model, intf, prop):
137
+ if prop in intf:
138
+ model[prop] = intf[prop]
139
+
140
+
141
+ def merge_model_intf(intf_data, model_intf, class_name, intf_name):
142
+ mdb_props = intf_data.get("properties", {})
143
+ if "properties" not in model_intf:
144
+ model_intf["properties"] = {}
145
+ model_props = model_intf["properties"]
146
+ for prop in model_props.keys():
147
+ if prop not in mdb_props:
148
+ raise RuntimeError(f"model.json中类{class_name}接口{intf_name}的属性{prop}在mdb_interface中没有被定义")
149
+ if mdb_props and "virtual" in intf_data:
150
+ model_props["priority"] = {
151
+ "baseType": "U8",
152
+ "default": 0
153
+ if "priority" not in model_intf
154
+ else model_intf["priority"],
155
+ }
156
+ intf_info = {"class_name": class_name, "intf_name": intf_name}
157
+ for prop, prop_data in mdb_props.items():
158
+ merge_props_and_data(intf_info, prop, model_props, prop_data, CHECK_PROPS_SETTINGS)
159
+
160
+ merge_when_intf_exist(model_intf, intf_data, "methods", class_name, intf_name)
161
+ merge_when_intf_exist(model_intf, intf_data, "signals", class_name, intf_name)
162
+ copy_when_exist(model_intf, intf_data, "package")
163
+ copy_when_exist(model_intf, intf_data, "virtual")
164
+ copy_when_exist(model_intf, intf_data, "default")
165
+
166
+
167
+ def append_object_prop_intf(mds_data, mdb_data):
168
+ object_prop_intf = "bmc.kepler.Object.Properties"
169
+ if object_prop_intf not in mds_data:
170
+ mds_data[object_prop_intf] = {}
171
+ if object_prop_intf not in mdb_data:
172
+ mdb_data.append(object_prop_intf)
173
+
174
+
175
+ def merge_model_class(class_name, mds_class, mdb_obj, mdb_path):
176
+ if "package" in mdb_obj[class_name]:
177
+ mds_class["package"] = mdb_obj[class_name]["package"]
178
+ append_object_prop_intf(mds_class["interfaces"], mdb_obj[class_name]["interfaces"])
179
+ for intf_name in mdb_obj[class_name]["interfaces"]:
180
+ if intf_name not in mds_class["interfaces"]:
181
+ raise RuntimeError(f"model.json中类{class_name}未配置资源树接口{intf_name}")
182
+ for item in mds_class["interfaces"][intf_name]:
183
+ if item not in ["properties", "methods", "signals", "privilege"]:
184
+ raise RuntimeError(f"model.json中类{class_name}接口{intf_name}的字段{item}超出取值范围")
185
+
186
+ intf_json = utils.get_intf(intf_name, mdb_path)
187
+ if "implement" in intf_json[intf_name]:
188
+ mds_class["interfaces"][intf_name] = utils.generate_default(
189
+ intf_json, mdb_path
190
+ )[intf_name]
191
+ if "defs" in intf_json:
192
+ mds_class["interfaces"][intf_name]["defs"] = intf_json["defs"]
193
+
194
+ merge_model_intf(intf_json[intf_name], mds_class["interfaces"][intf_name], class_name, intf_name)
195
+
196
+
197
+ def get_class_name(path):
198
+ return list(filter(None, path.split("/")))[-1]
199
+
200
+
201
+ def get_parent_path(origin_model, class_data):
202
+ if "parent" in class_data and class_data["parent"] in origin_model and \
203
+ "path" in origin_model[class_data["parent"]]:
204
+ return get_parent_path(origin_model, origin_model[class_data["parent"]]) \
205
+ + "/" + utils.cut_ids(class_data["path"])
206
+ else:
207
+ return utils.cut_ids(class_data["path"])
208
+
209
+
210
+ def check_class_property_name_conflict(class_name, class_data):
211
+ prop_names = {}
212
+
213
+ for prop_name, prop_config in class_data.get("properties", {}).items():
214
+ name = prop_config.get('alias', prop_name)
215
+ if name in prop_names:
216
+ raise RuntimeError(f"在model.json文件{class_name}类中发现重名私有属性{prop_name}")
217
+ else:
218
+ prop_names[name] = True
219
+
220
+ for interface, intf_data in class_data.get("interfaces", {}).items():
221
+ for prop_name, prop_config in intf_data.get("properties", {}).items():
222
+ name = prop_config.get('alias', prop_name)
223
+ if name in prop_names:
224
+ raise RuntimeError(f"在model.json文件{class_name}类的{interface}接口中发现重名资源树属性{prop_name}")
225
+ else:
226
+ prop_names[name] = True
227
+
228
+
229
+ def check_property_name_conflict(origin_model):
230
+ for class_name, class_data in origin_model.items():
231
+ check_class_property_name_conflict(class_name, class_data)
232
+
233
+
234
+ def merge_model(origin_model, mdb_path):
235
+ for class_name, class_data in origin_model.items():
236
+ if "path" in class_data and class_name != "defs":
237
+ class_path = get_parent_path(origin_model, class_data)
238
+ mdb_obj = utils.get_path(class_name, mdb_path, class_path)
239
+ merge_model_class(class_name, class_data, mdb_obj, mdb_path)
240
+
241
+ check_property_name_conflict(origin_model)
242
+
243
+
244
+ def save_merged_json(of_name, model):
245
+ paths = of_name.split("/")
246
+ paths.pop()
247
+ merged_json_path = os.path.realpath(("/").join(paths))
248
+ if not os.path.exists(merged_json_path):
249
+ os.mkdir(merged_json_path)
250
+ save_file(of_name, model)
251
+
252
+
253
+ def check_method_cmd_name(class_name, intf_name, method, method_data, cmds):
254
+ if "cmdName" in method_data:
255
+ cmd_name = method_data["cmdName"]
256
+ if cmd_name in cmds:
257
+ if intf_name != cmds[cmd_name][0] or method != cmds[cmd_name][1]:
258
+ raise RuntimeError(f"model.json文件的{class_name}类的{intf_name}接口的{method}方法的cmdName {cmd_name}已被使用,请重新命名")
259
+ else:
260
+ cmds[cmd_name] = [intf_name, method]
261
+
262
+
263
+ def check_cmd_name(mds_class, cmd_file):
264
+ cmds = {}
265
+ if os.path.exists(cmd_file):
266
+ load_f = os.fdopen(os.open(cmd_file, os.O_RDONLY, stat.S_IRUSR), "r")
267
+ try:
268
+ cmds = OrderedDict(json.load(load_f))
269
+ except json.JSONDecodeError as e:
270
+ log.debug(f"JSON 解析错误: {e}")
271
+ load_f.close()
272
+
273
+ for class_name, class_data in mds_class.items():
274
+ for intf_name, intf_data in class_data.get("interfaces", {}).items():
275
+ for method, method_data in intf_data.get("methods", {}).items():
276
+ check_method_cmd_name(class_name, intf_name, method, method_data, cmds)
277
+
278
+ save_file(cmd_file, cmds)
279
+
280
+
281
+ def generate(if_name, of_name, mdb_path, cmd_file):
282
+ load_dict = {}
283
+ if os.path.exists(if_name):
284
+ load_f = os.fdopen(os.open(if_name, os.O_RDONLY, stat.S_IRUSR), "r")
285
+ load_dict = OrderedDict(json.load(load_f))
286
+ load_f.close()
287
+
288
+ if Utils.get_lua_codegen_version() >= 16:
289
+ check_cmd_name(load_dict, cmd_file)
290
+ merge_model(load_dict, mdb_path)
291
+ save_merged_json(of_name, load_dict)
292
+
293
+
294
+ def usage():
295
+ logging.info("gen_schema.py -i <inputfile> -o <outfile>")
296
+
297
+
298
+ def main(argv):
299
+ m_input = ""
300
+ output = ""
301
+ mdb_path = ""
302
+ try:
303
+ opts, _ = getopt.getopt(
304
+ argv, "hi:o:d:c:", ["help", "input=", "out=", "mdb_interfac_path", "cmdfile="]
305
+ )
306
+ except getopt.GetoptError:
307
+ help()
308
+ return
309
+ for opt, arg in opts:
310
+ if opt in ("-h", "--help"):
311
+ usage()
312
+ return
313
+ elif opt in ("-i", "--input"):
314
+ m_input = arg
315
+ elif opt in ("-o", "--out"):
316
+ output = arg
317
+ elif opt in ("-d", "--dir"):
318
+ mdb_path = arg
319
+ elif opt in ("-c", "--cmdfile"):
320
+ cmd_file = arg
321
+ else:
322
+ raise RuntimeError("不支持的选项: {}".format(opt))
323
+ if not m_input or not output:
324
+ usage()
325
+ return
326
+ generate(m_input, output, mdb_path, cmd_file)
327
+
328
+
329
+ if __name__ == "__main__":
330
+ main(sys.argv[1:])
@@ -0,0 +1,85 @@
1
+ #!/usr/bin/env python3
2
+ # coding=utf-8
3
+ # Copyright (c) 2024 Huawei Technologies Co., Ltd.
4
+ # openUBMC is licensed under Mulan PSL v2.
5
+ # You can use this software according to the terms and conditions of the Mulan PSL v2.
6
+ # You may obtain a copy of Mulan PSL v2 at:
7
+ # http://license.coscl.org.cn/MulanPSL2
8
+ # THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
9
+ # EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
10
+ # MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
11
+ # See the Mulan PSL v2 for more details.
12
+
13
+ HW_DEFINE_ATTR_OPTION_DICT = {"validate": "", "readonly": False, "rename": ""}
14
+ HW_DEFINE_MESSAGE_OPTION_DICT = {}
15
+
16
+
17
+ def merge_options(new_attr: dict, old_attr: dict, self_define_option_set: dict):
18
+ options = old_attr.get("options")
19
+ if not isinstance(options, dict):
20
+ return
21
+ for option in options.keys():
22
+ if option in self_define_option_set:
23
+ new_attr.setdefault(option, options.get(option))
24
+
25
+
26
+ def merge_property_list(new_property_dict, property_list):
27
+ for pt in property_list:
28
+ if not isinstance(pt, dict):
29
+ continue
30
+ attr_name = pt.get("name")
31
+ new_attr = new_property_dict.get(attr_name)
32
+ if not isinstance(new_attr, dict):
33
+ continue
34
+ merge_options(new_attr, pt, HW_DEFINE_ATTR_OPTION_DICT)
35
+
36
+
37
+ def merge_message(new_message: dict, message: dict):
38
+ merge_options(new_message, message, HW_DEFINE_MESSAGE_OPTION_DICT)
39
+ property_list = message.get("properties")
40
+ if not isinstance(property_list, list):
41
+ return
42
+ new_property_dict = new_message.get("properties")
43
+ if not isinstance(new_property_dict, dict):
44
+ return
45
+
46
+ merge_property_list(new_property_dict, property_list)
47
+
48
+
49
+ def merge_message_list(new_message_dict: dict, message_list: list):
50
+ for message in message_list:
51
+ name = message.get("name")
52
+ new_message = new_message_dict.get(name)
53
+ if not new_message:
54
+ continue
55
+ merge_message(new_message, message)
56
+
57
+
58
+ def merge_json(redfish_json: dict, proto_json: dict):
59
+ if not isinstance(redfish_json, dict) or not isinstance(proto_json, dict):
60
+ return redfish_json
61
+ message_list = proto_json.get("data")
62
+ if not isinstance(message_list, list):
63
+ return redfish_json
64
+ new_message_dict = redfish_json.get("definitions")
65
+ if not isinstance(new_message_dict, dict):
66
+ return redfish_json
67
+ merge_message_list(new_message_dict, message_list)
68
+ return redfish_json
69
+
70
+
71
+ def is_need_specify_option(key: str, value, option_dict: dict) -> bool:
72
+ if key not in option_dict:
73
+ return False
74
+ default_value = option_dict.get(key)
75
+ if default_value == value:
76
+ return False
77
+ return True
78
+
79
+
80
+ def is_message_option(key: str, value) -> bool:
81
+ return is_need_specify_option(key, value, HW_DEFINE_MESSAGE_OPTION_DICT)
82
+
83
+
84
+ def is_attr_option(key: str, value) -> bool:
85
+ return is_need_specify_option(key, value, HW_DEFINE_ATTR_OPTION_DICT)
@@ -0,0 +1,47 @@
1
+ #!/usr/bin/env python3
2
+ # coding=utf-8
3
+ # Copyright (c) 2024 Huawei Technologies Co., Ltd.
4
+ # openUBMC is licensed under Mulan PSL v2.
5
+ # You can use this software according to the terms and conditions of the Mulan PSL v2.
6
+ # You may obtain a copy of Mulan PSL v2 at:
7
+ # http://license.coscl.org.cn/MulanPSL2
8
+ # THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
9
+ # EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
10
+ # MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
11
+ # See the Mulan PSL v2 for more details.
12
+
13
+ import json
14
+ import os
15
+ import stat
16
+ import subprocess
17
+
18
+ proto_cvt_plugin_path = os.path.abspath(os.path.join(os.path.dirname(__file__), "proto_plugin.py"))
19
+
20
+
21
+ def proto_to_json(proto_root_path: str, relative_path: str, proto_json_root_path: str):
22
+ os.makedirs(proto_json_root_path, exist_ok=True)
23
+ cmd = [
24
+ "protoc",
25
+ f"--plugin=protoc-gen-custom={proto_cvt_plugin_path}",
26
+ f"--custom_out={proto_json_root_path}",
27
+ f"-I{proto_root_path}",
28
+ relative_path
29
+ ]
30
+ subprocess.run(cmd, shell=False)
31
+
32
+
33
+ def parse(proto_root_path, relative_path: str, proto_json_root_path: str) -> dict:
34
+ json_file_path = os.path.abspath(os.path.join(proto_json_root_path, relative_path + ".json"))
35
+ proto_file_path = os.path.abspath(os.path.join(proto_root_path, relative_path))
36
+ if not os.path.exists(proto_file_path):
37
+ return {}
38
+ if not os.path.exists(json_file_path):
39
+ proto_to_json(proto_root_path, relative_path, proto_json_root_path)
40
+ json_stat = os.stat(json_file_path)
41
+ proto_stat = os.stat(proto_file_path)
42
+ if json_stat[stat.ST_MTIME] <= proto_stat[stat.ST_MTIME]:
43
+ proto_to_json(proto_root_path, relative_path, proto_json_root_path)
44
+ if not os.path.exists(json_file_path):
45
+ return {}
46
+ with open(json_file_path, "r", encoding="utf-8") as fd:
47
+ return json.load(fd)
@@ -0,0 +1,140 @@
1
+ #!/usr/bin/env python3
2
+ # coding=utf-8
3
+ # Copyright (c) 2024 Huawei Technologies Co., Ltd.
4
+ # openUBMC is licensed under Mulan PSL v2.
5
+ # You can use this software according to the terms and conditions of the Mulan PSL v2.
6
+ # You may obtain a copy of Mulan PSL v2 at:
7
+ # http://license.coscl.org.cn/MulanPSL2
8
+ # THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
9
+ # EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
10
+ # MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
11
+ # See the Mulan PSL v2 for more details.
12
+
13
+ import itertools
14
+ import json
15
+ import sys
16
+ import types_pb2
17
+ import ipmi_types_pb2
18
+
19
+ from google.protobuf.descriptor_pb2 import DescriptorProto, \
20
+ EnumDescriptorProto, FieldDescriptorProto, ServiceDescriptorProto
21
+ from google.protobuf.compiler.plugin_pb2 import CodeGeneratorRequest, CodeGeneratorResponse
22
+
23
+ BASIC_TYPES = {
24
+ getattr(FieldDescriptorProto, t):
25
+ t
26
+ for t in dir(FieldDescriptorProto)
27
+ if t.startswith("TYPE_")
28
+ }
29
+
30
+ ALLOW_BASIC_TYPES = {
31
+ FieldDescriptorProto.TYPE_BOOL: "bool",
32
+ FieldDescriptorProto.TYPE_STRING: "string",
33
+ FieldDescriptorProto.TYPE_INT32: "int32",
34
+ FieldDescriptorProto.TYPE_UINT32: "uint32",
35
+ FieldDescriptorProto.TYPE_INT64: "int64",
36
+ FieldDescriptorProto.TYPE_UINT64: "uint64",
37
+ FieldDescriptorProto.TYPE_FLOAT: "float",
38
+ FieldDescriptorProto.TYPE_DOUBLE: "double",
39
+ FieldDescriptorProto.TYPE_BYTES: "bytes",
40
+ }
41
+
42
+
43
+ def get_type_name(n_type, t_name, label):
44
+ if n_type == FieldDescriptorProto.TYPE_MESSAGE or n_type == FieldDescriptorProto.TYPE_ENUM:
45
+ if t_name.startswith("."):
46
+ return t_name[1:]
47
+ return t_name
48
+ elif n_type in ALLOW_BASIC_TYPES:
49
+ type_allow = ALLOW_BASIC_TYPES[n_type]
50
+ return type_allow if label != FieldDescriptorProto.LABEL_REPEATED else f'{type_allow}[]'
51
+ raise RuntimeError("无效类型 {}({})".format(BASIC_TYPES[n_type], n_type))
52
+
53
+
54
+ def traverse(proto_file):
55
+ def _traverse(package, items):
56
+ for item in items:
57
+ yield item, package
58
+
59
+ return itertools.chain(
60
+ _traverse(proto_file.package, proto_file.enum_type),
61
+ _traverse(proto_file.package, proto_file.message_type),
62
+ _traverse(proto_file.package, proto_file.service),
63
+ )
64
+
65
+
66
+ def process_item(item, package):
67
+ data = {
68
+ 'package': package or 'root',
69
+ 'name': item.name,
70
+ 'options': {op.name: item.options.Extensions[op] for op in item.options.Extensions}
71
+ }
72
+
73
+ if isinstance(item, DescriptorProto):
74
+ data.update({
75
+ 'type': 'Message',
76
+ "properties": [{
77
+ "name": f.name,
78
+ 'type': get_type_name(f.type, f.type_name, f.label),
79
+ "options": {op.name: f.options.Extensions[op] for op in f.options.Extensions},
80
+ 'id': f.number,
81
+ 'repeated': f.label == FieldDescriptorProto.LABEL_REPEATED
82
+ } for f in item.field],
83
+ "nested_type": [process_item(nested_item, package) for nested_item in item.nested_type]})
84
+ elif isinstance(item, EnumDescriptorProto):
85
+ data.update({
86
+ 'type': 'Enum',
87
+ 'values': [{
88
+ 'name': v.name,
89
+ 'value': v.number,
90
+ 'id': v.number
91
+ } for v in item.value]
92
+ })
93
+ return data
94
+
95
+
96
+ def generate_code(req, resp):
97
+ imports = []
98
+ for proto_file in req.proto_file:
99
+ if proto_file.name not in req.file_to_generate:
100
+ imports.append(proto_file.name)
101
+ continue
102
+
103
+ o_put = []
104
+ service = []
105
+ for item, package in traverse(proto_file):
106
+ if isinstance(item, ServiceDescriptorProto):
107
+ [service.append({
108
+ 'method_options': {op.name: v.options.Extensions[op] for op in v.options.Extensions},
109
+ 'options': {op.name: item.options.Extensions[op] for op in item.options.Extensions},
110
+ 'name': v.name,
111
+ 'req': v.input_type,
112
+ 'rsp': v.output_type,
113
+ }) for v in item.method]
114
+ else:
115
+ o_put.append(process_item(item, package))
116
+
117
+ file = resp.file.add()
118
+ file.name = proto_file.name + '.json'
119
+ file.content = json.dumps({
120
+ 'imports': imports,
121
+ 'dependency': [v for v in proto_file.dependency],
122
+ 'data': o_put,
123
+ 'service': service,
124
+ 'filename': proto_file.name,
125
+ 'package': proto_file.package,
126
+ 'options': {op.name: proto_file.options.Extensions[op] for op in proto_file.options.Extensions}
127
+ }, indent=2)
128
+
129
+
130
+ def read_data():
131
+ data = sys.stdin.buffer.read()
132
+ return data
133
+
134
+ if __name__ == '__main__':
135
+ request = CodeGeneratorRequest()
136
+ request.ParseFromString(read_data())
137
+ response = CodeGeneratorResponse()
138
+ generate_code(request, response)
139
+ output = response.SerializeToString()
140
+ sys.stdout.buffer.write(output)