rtc-template.py
Go to the documentation of this file.
00001 #!/usr/bin/env python
00002 # -*- python -*-
00003 #
00004 #  @file rtc-template
00005 #  @brief rtc-template RTComponent source code generator tool
00006 #  @date $Date: 2007-10-09 07:19:15 $
00007 #  @author Noriaki Ando <n-ando@aist.go.jp>
00008 # 
00009 #  Copyright (C) 2004-2008
00010 #      Task-intelligence Research Group,
00011 #      Intelligent Systems Research Institute,
00012 #      National Institute of
00013 #          Advanced Industrial Science and Technology (AIST), Japan
00014 #      All rights reserved.
00015 # 
00016 #  $Id: rtc-template 1815 2010-01-27 20:26:57Z n-ando $
00017 #
00018 
00019 import getopt, sys
00020 import time
00021 import re
00022 import os
00023 import yaml
00024 import copy
00025 
00026 default_profile="""
00027 rtcProfile: 
00028   version: "1.0"
00029   id: # RTC:SampleVendor.SampleCategory.SampleComponent:1.0.0
00030   basicInfo:
00031     name: ""
00032     description: ""
00033     version: 1.0.0
00034     vendor: SampleVendor
00035     category: ""
00036     componentType: STATIC
00037     activityType: PERIODIC
00038     componentKind: DataFlowComponent
00039     maxInstances: 1
00040     abstract: ""
00041     executionRate: 1000.0
00042     executionType: PeriodicExecutionContext
00043     creationDate:
00044       day: ""
00045       hour: ""
00046       minute: ""
00047       month: ""
00048       second: ""
00049       year: ""
00050     updateDate:
00051       day: 17
00052       hour: 14
00053       minute: 0
00054       month: 4
00055       second: 0
00056       year: 2008
00057     "rtcDoc::doc":
00058       algorithm: ""
00059       creator: ""
00060       description: ""
00061       inout: ""
00062       license: ""
00063       reference: ""
00064     "rtcExt::versionUpLog": 
00065       - "2008/04/18 14:00:00:Ver1.0"
00066       - "2008/04/18 17:00:00:Ver1.1"
00067   language: 
00068     java: 
00069       library: 
00070         - library1
00071   actions: 
00072     onAborting:
00073       "rtcDoc::doc":
00074         description: on_aborting description
00075         postCondition: on_aborting Post_condition
00076         preCondition: on_aborting Pre_condition
00077       implemented: true
00078     onActivated:
00079       "rtcDoc::doc":
00080         description: on_activated description
00081         postCondition: on_activated Post_condition
00082         preCondition: on_activated Pre_condition
00083       implemented: true
00084     onDeactivated:
00085       "rtcDoc::doc":
00086         description: on_deactivated description
00087         postCondition: on_deactivated Post_condition
00088         preCondition: on_deactivated Pre_condition
00089     onError:
00090       "rtcDoc::doc":
00091         description: on_error description
00092         postCondition: on_error Post_condition
00093         preCondition: on_error Pre_condition
00094     onExecute:
00095       "rtcDoc::doc":
00096         description: on_execute description
00097         postCondition: on_execute Post_condition
00098         preCondition: on_execute Pre_condition
00099     onFinalize:
00100       "rtcDoc::doc":
00101         description: on_finalize description
00102         postCondition: on_finalize Post_condition
00103         preCondition: on_finalize Pre_condition
00104     onInitialize:
00105       "rtcDoc::doc":
00106         description: on_initialize description
00107         postCondition: on_initialize Post_condition
00108         preCondition: on_initialize Pre_condition
00109       implemented: true
00110     onRateChanged:
00111       "rtcDoc::doc":
00112         description: on_rate_changed description
00113         postCondition: on_rate_changed Post_condition
00114         preCondition: on_rate_changed Pre_condition
00115     onReset:
00116       "rtcDoc::doc":
00117         description: on_reset description
00118         postCondition: on_reset Post_condition
00119         preCondition: on_reset Pre_condition
00120     onShutdown:
00121       "rtcDoc::doc":
00122         description: on_shutdown description
00123         postCondition: on_shutdown Post_condition
00124         preCondition: on_shutdown Pre_condition
00125       implemented: true
00126     onStartup:
00127       "rtcDoc::doc":
00128         description: on_startup description
00129         postCondition: on_startup Post_condition
00130         preCondition: on_startup Pre_condition
00131     onStateUpdate:
00132       "rtcDoc::doc":
00133         description: on_state_update description
00134         postCondition: on_state_update Post_condition
00135         preCondition: on_state_update Pre_condition
00136   dataPorts: 
00137     -
00138       name: inport1
00139       portType: DataInPort
00140       type: "RTC::TimedLong"
00141       interfaceType: CorbaPort
00142       dataflowType: "Push,Pull"
00143       subscriprionType: "Periodic,New,Flush"
00144       idlFile: DataPort1.idl
00145       "rtcDoc::doc":
00146         type: In1Type
00147         description: In1Description
00148         number: In1Number
00149         occerrence: In1Occerrence
00150         operation: In1Operation
00151         semantics: In1Semantics
00152         unit: In1Unit
00153       "rtcExt::position": LEFT
00154       "rtcExt::varname": In1Var
00155   servicePorts: 
00156     -
00157       name: SrvPort1
00158       "rtcDoc::doc":
00159         description: ServicePort1 description
00160         ifdescription: ServicePort1 I/F description
00161       "rtcExt::position": LEFT
00162       serviceInterface: 
00163         -
00164           direction: Provided
00165           "rtcDoc::doc":
00166             description: if1 Description
00167             docArgument: if1 Argument
00168             docException: if1 Exception
00169             docPostCondition: if1 PostCond
00170             docPreCondition: if1 PreCond
00171             docReturn: if1 Return
00172           idlFile: IF1Idlfile.idl
00173           instanceName: IF1Instance
00174           name: S1IF1
00175           path: IF1SearchPath
00176           type: IF1Type
00177           varname: IF1VarName
00178   configurationSet: 
00179     configuration: 
00180       - 
00181         name: config1
00182         type: int
00183         varname: var1
00184         defaultValue: ""
00185         "rtcDoc::doc":
00186           constraint: config_constraint1
00187           dataname: dataname1
00188           defaultValue: default1
00189           description: config_Desc1
00190           range: config_range1
00191           unit: config_unit1
00192   parameters: 
00193     -
00194       defaultValue: param_def1
00195       name: param1
00196     -
00197       defaultValue: param_def2
00198       name: param2
00199 
00200 """
00201 
00202 
00203 class Struct:
00204         def __init__(self):
00205                 return
00206 
00207 libdir_path = os.popen("rtm-config --libdir", "r").read().split("\n")
00208 if libdir_path[0] != '':
00209         pyhelper_path = libdir_path[0] + "/py_helper"
00210         sys.path.append(pyhelper_path)
00211 else:
00212         pyhelper_path = os.environ['RTM_ROOT'] + "/utils/rtc-template"
00213         sys.path.append(pyhelper_path)
00214 
00215 # Option format
00216 opt_args_fmt = ["help",
00217                 "module-name=",
00218                 "module-type=",
00219                 "module-desc=",
00220                 "module-version=",
00221                 "module-vendor=",
00222                 "module-category=",
00223                 "module-comp-type=",
00224                 "module-act-type=",
00225                 "module-max-inst=",
00226                 "module-lang=",
00227                 "config=",
00228                 "inport=",
00229                 "outport=",
00230                 "service=",
00231                 "service-idl=",
00232                 "consumer=",
00233                 "consumer-idl=",
00234                 "idl-include=",
00235                 "backend="]
00236 
00237 
00238 def usage_short():
00239         """
00240         Help message
00241         """
00242         print """
00243 Usage: rtc-template [OPTIONS]
00244 
00245 Options:
00246 
00247     [-h]                                  Print short help.
00248     [--help]                              Print details help.
00249     [--backend[=backend] or -b]           Specify template code generator.
00250     [--module-name[=name]]                Your module name.
00251     [--module-desc[=description]]         Module description.
00252     [--module-version[=version]]          Module version.
00253     [--module-vendor[=vendor]]            Module vendor.
00254     [--module-category[=category]]        Module category.
00255     [--module-comp-type[=component_type]] Component type.
00256     [--module-act-type[=activity_type]]   Component's activity type.
00257     [--module-max-inst[=max_instance]]    Number of maximum instance.
00258     [--module-lang[=language]]            Language.
00259     [--config[=ParamName:Type:Default]]   Configuration variable.
00260     [--inport[=PortName:Type]]            InPort's name and type.
00261     [--outport[=PortName:Type]]           OutPort's name and type
00262     [--service[=PortName:Name:Type]]      Service Provider Port
00263     [--service-idl[=IDL_file]]            IDL file name for service
00264     [--consumer[=PortName:Name:Type]]     Service Consumer Port
00265     [--consumer-idl[=IDL_file]]           IDL file name for consumer
00266     [--idl-include=[path]]                Search path for IDL compile
00267 
00268 """
00269 def usage_long():
00270         """
00271         Help message
00272         """
00273         print """
00274     --output[=output_file]:
00275         Specify base name of output file. If 'XXX' is specified,
00276         C++ source codes XXX.cpp, XXX.h, XXXComp.cpp Makefile.XXX is generated.
00277 
00278     --module-name[=name]:
00279         Your component's base name. This string is used as module's
00280         name and component's base name. A generated new component
00281         class name is also names as this RTC_MODULE_NAME.
00282         Only alphabetical and numerical characters are acceptable.
00283 
00284     --module-desc[=description]:
00285         Short description. If space characters are included, string should be
00286         quoted.
00287 
00288     --module-version[=version]:
00289         Your module version. ex. 1.0.0
00290 
00291     --module-vendor[=vendor]:
00292         Vendor's name of this component.
00293 
00294     --module-category[=category]:
00295         This component module's category. ex. Manipulator MobileRobot, etc...
00296 
00297     --module-comp-type[=component_type]:
00298         Specify component type.
00299             'STATIC', 'UNIQUE', 'COMMUTATIVE' are acceptable.
00300 
00301     --module-act-type[=activity_type]:
00302         Specify component activity's type.
00303         'PERIODIC', 'SPORADIC', 'EVENT_DRIVEN' ace acceptable.
00304 
00305     --module-max-inst[=max_instance]:
00306         Specify maximum number of component instance.
00307 
00308     --config=[ParamName:Type:Default]:
00309         Specify configuration value. The 'ParamName' is used as the
00310         configuration value identifier. This character string is also used as
00311         variable name in the source code. The 'Type' is type of configuration
00312         value. The type that can be converted to character string is allowed.
00313         In C++ language, the type should have operators '<<' and '>>' that
00314         are defined as
00315         'istream& operator<<(Type)'
00316         and
00317         'ostream& operator>>(Type)'.
00318 
00319     --inport=[PortName:Type]:
00320         Specify InPort's name and type. 'PortName' is used as this InPort's
00321         name. This string is also used as variable name in soruce code.
00322         'Type' is InPort's variable type. The acceptable types are,
00323         Timed[ Short | Long | UShort | ULong | Float | Double | Char | Boolean
00324         | Octet | String ] and its sequence types.
00325 
00326     --outport=[PortName:Type]:
00327         Specify OutPort's name and type. 'PortName' is used as this OutPort's
00328         name. This string is also used as variable name in soruce code.
00329         'Type' is OutPort's variable type. The acceptable types are,
00330         Timed[ Short | Long | UShort | ULong | Float | Double | Char | Boolean
00331         | Octet | String ] and its sequence types.
00332                 
00333     --service=[PortName:Name:Type]:
00334         Specify service name, type and port name.
00335         PortName: The name of Port to which the interface belongs.
00336               This name is used as CorbaPort's name.
00337         Name: The name of the service interface. This name is used as 
00338               the name of the interface, instance name and variable name.
00339         Type: The type of the serivce interface.
00340               This name is used as type name of the service.
00341 
00342     --service-idl=[IDL filename]:
00343         Specify IDL file of service interface.
00344         For simplicity, please define one interface in one IDL file, although
00345         this IDL file can include two or more interface definition,
00346                 
00347     --consumer=[PortName:Name:Type]:
00348         Specify consumer name, type and port name.
00349         PortName: The name of Port to which the consumer belongs.
00350               This name is used as CorbaPort's name.
00351         Name: The name of the consumer. This name is used as 
00352               the name of the consumer, instance name and variable name.
00353         Type: The serivce interface type that is required by the consumer.
00354               This name is used as type name of the consumer.
00355 
00356     --consumer-idl=[IDL filename]:
00357         Specify IDL file of service consumer.
00358         For simplicity, please define one interface in one IDL file, although
00359         this IDL file can include two or more interface definition,
00360         
00361 
00362 Example:
00363     rtc-template -bcxx \\
00364     --module-name=Sample --module-desc='Sample component' \\
00365     --module-version=0.1 --module-vendor=AIST --module-category=Generic \\
00366     --module-comp-type=DataFlowComponent --module-act-type=SPORADIC \\
00367     --module-max-inst=10  \\
00368     --config=int_param0:int:0 --config=int_param1:int:1 \\
00369     --config=double_param0:double:3.14 --config=double_param1:double:9.99 \\
00370     --config="str_param0:std::string:hoge" \\
00371     --config="str_param1:std::string:foo" \\
00372     --inport=Ref:TimedFloat --inport=Sens:TimedFloat \\
00373     --outport=Ctrl:TimedDouble --outport=Monitor:TimedShort \\
00374     --service=MySvcPort:myservice0:MyService \\
00375     --consumer=YourSvcPort:yourservice0:YourService \\
00376     --service-idl=MyService.idl --consumer-idl=YourService.idl
00377 
00378 """
00379         return
00380 
00381 def usage():
00382         usage_short()
00383         usage_long()
00384         return
00385                 
00386 
00387 def CreateBasicInfo(opts):
00388         """
00389         MakeModuleProfile
00390 
00391         Create ModuleProfile list from command options
00392         """
00393         mapping = {
00394                 'name': 'name',
00395                 'desc': 'description',
00396                 'version': 'version',
00397                 'vendor': 'vendor',
00398                 'category': 'category',
00399                 'comp-type': 'componentType',
00400                 'act-type': 'activityType',
00401                 'type': 'componentKind',
00402                 'max-inst': 'maxInstances'
00403                 }
00404         # default "basicInfo"
00405         prof = {
00406                 "name": "",
00407                 "description": "",
00408                 "version": "1.0.0",
00409                 "vendor": "",
00410                 "category": "",
00411                 "componentType": "STATIC",
00412                 "activityType": "PERIODIC",
00413                 "componentKind": "DataFlowComponent",
00414                 "maxInstances": "1",
00415                 "abstract": "",
00416                 "executionRate": "1000.0",
00417                 "executionType": "PeriodicExecutionContext",
00418                 "creationDate":
00419                         {
00420                         "day": "",
00421                         "hour": "",
00422                         "minute": "",
00423                         "month": "",
00424                         "second": "",
00425                         "year": ""
00426                         },
00427                 "updateDate":
00428                         {
00429                         "year": "",
00430                         "month": "",
00431                         "day": "",
00432                         "hour": "",
00433                         "minute": "",
00434                         "second": "",
00435                         },
00436                 "rtcDoc::doc":
00437                         {
00438                         "algorithm": "",
00439                         "creator": "",
00440                         "description": "",
00441                         "inout": "",
00442                         "license": "",
00443                         "reference": ""
00444                         },
00445                 "rtcExt::versionUpLog": []
00446                 }
00447 
00448         # obtain --module-xxx options' values
00449         for opt, arg in opts:
00450                 if opt.find("--module-") == 0:
00451                         var = opt.replace("--module-","")
00452                         if prof.has_key(mapping[var]):
00453                                 prof[mapping[var]] = arg
00454         # set creationDate
00455         cDate = time.localtime()
00456         i = 0
00457         cDateKey = ['year', 'month', 'day', 'hour', 'minute', 'second']
00458         for key in cDateKey:
00459                 prof["creationDate"][key] = cDate[i]
00460                 i += 1
00461         # check empty values
00462         empty = []
00463         for key in prof.keys():
00464                 if prof[key] == "":
00465                         empty.append(key)
00466 
00467         return prof
00468 
00469 def CreateActions(opts):
00470         actnames = [
00471                 "onInitialize",
00472                 "onFinalize",
00473                 "onActivated",
00474                 "onDeactivated",
00475                 "onAborting",
00476                 "onError",
00477                 "onReset",
00478                 "onExecute",
00479                 "onStateUpdate",
00480                 "onShutdown",
00481                 "onStartup",
00482                 "onRateChanged",
00483                 ]
00484 
00485         actions = {}
00486         for a in actnames:
00487                 actions[a] = {
00488                         "rtcDoc::doc": {
00489                                 "description": a + " description",
00490                                 "postCondition": a + " Post_condition",
00491                                 "preCondition": a + " Pre_condition"
00492                                 },
00493                         "implemented": True
00494                         }
00495         return actions
00496 
00497 def CreateConfigurationSet(opts):
00498         """
00499         MakeConfigurationParameters
00500 
00501         Create Configuration list from command options
00502         """
00503         prof_list = []
00504         prof = {
00505                 "name": "",
00506                 "type": "",
00507                 "varname": "",
00508                 "defaultValue": "",
00509                 "rtcDoc::doc":
00510                         {
00511                         "type": "type", # type
00512                         "constraint": "constraint",
00513                         "dataname": "dataname",
00514                         "defaultValue": "default",
00515                         "description": "description",
00516                         "range": "range",
00517                         "unit": "unit"
00518                         }
00519                 }
00520         for opt, arg in opts:
00521                 if opt == ("--config"):
00522                         try:
00523                                 # For C++ scope resolution operator 
00524                                 arg = re.sub("::", "@@", arg)
00525                                 name, type, default = arg.split(":")
00526                                 name    = re.sub("@@", "::", name)
00527                                 type    = re.sub("@@", "::", type)
00528                                 default = re.sub("@@", "::", default)
00529                         except:
00530                                 sys.stderr.write("Invalid option: " \
00531                                                          + opt \
00532                                                          + "=" \
00533                                                          + arg)
00534                         tmp = copy.deepcopy(prof)
00535                         tmp["name"] = name
00536                         tmp["varname"] = name
00537                         tmp["l_name"] = name.lower()
00538                         tmp["u_name"] = name.upper()
00539                         tmp["type"] = type
00540                         tmp["defaultValue"] = default
00541                         tmp["rtcDoc::doc"]["defaultValue"] = default
00542                         prof_list.append(tmp)
00543         return {'configuration': prof_list}
00544 
00545 
00546 def CreateDataPorts(opts):
00547         """
00548         MakePortProfile
00549 
00550         Create PortProfile list from command options
00551         """
00552         prof_list = []
00553         prof = {
00554                 "name": "",
00555                 "portType": "",
00556                 "type": "",
00557                 "interfaceType": "CorbaPort",
00558                 "dataflowType": "Push,Pull",
00559                 "subscriptionType": "Periodic,New,Flush",
00560                 "idlFile": "",
00561                 "rtcDoc::doc":
00562                         {
00563                         "type": "",
00564                         "description": "",
00565                         "number": "",
00566                         "occerrence": "",
00567                         "operation": "",
00568                         "semantics": "",
00569                         "unit": ""
00570                         },
00571                 "rtcExt::position": "",
00572                 "rtcExt::varname": ""
00573                 }
00574         cnt = 0
00575         portType = {"--inport": "DataInPort", "--outport": "DataOutPort"}
00576         position = {"--inport": "LEFT", "--outport": "RIGHT"}
00577         for opt, arg in opts:
00578                 if opt == "--inport" or opt == "--outport":
00579                         try:
00580                                 arg = re.sub("::", "@@", arg)
00581                                 name, type = arg.split(":")
00582                                 name    = re.sub("@@", "::", name)
00583                                 type    = re.sub("@@", "::", type)
00584                         except:
00585                                 sys.stderr.write("Invalid option: " \
00586                                                          + opt \
00587                                                          + "=" \
00588                                                          + arg)
00589                         tmp = copy.deepcopy(prof)
00590                         tmp["name"] = name
00591                         tmp["portType"] = portType[opt]
00592                         tmp["type"] = type
00593                         tmp["num"]  = cnt
00594                         tmp["rtcDoc::doc"]["type"] = type
00595                         tmp["rtcDoc::doc"]["number"] = cnt
00596                         tmp["rtcExt::varname"] = name
00597                         tmp["rtcExt::position"] = position[opt]
00598                         prof_list.append(tmp)
00599                         cnt += 1
00600         return prof_list
00601 
00602 
00603 def CreateServicePorts(opts):
00604         """
00605         MakePortInterface
00606 
00607         Create Port interface profile list from command options
00608         """
00609         prof_list = []
00610 
00611         prof = {
00612                 "name": "",
00613                 "rtcDoc::doc":
00614                         {
00615                         "description": "",
00616                         "ifdescription": "",
00617                         },
00618                 "rtcExt::position": "LEFT",
00619                 "serviceInterface": []
00620                 }
00621         ifprof = {
00622                 "name": "",
00623                 "type": "",
00624                 "direction": "",
00625                 "varname": "",
00626                 "instanceName": "",
00627                 "idlFile": "",
00628                 "path": "",
00629                 "rtcDoc::doc":
00630                         {
00631                         "description": "",
00632                         "docArgument": "",
00633                         "docException": "",
00634                         "docPostCondition": "",
00635                         "docPreCondition": "",
00636                         "docReturn": ""
00637                         }
00638                 }
00639 
00640         def findport(prof_list, port_name):
00641                 for p in prof_list:
00642                         if p["name"] == port_name:
00643                                 return p
00644                 return None
00645         def lr(port):
00646                 cnt = {"Provided": 0, "Required": 0}
00647                 for ifprof in port["serviceInterface"]:
00648                         cnt[ifprof["direction"]] += 1
00649                 if cnt["Provided"] < cnt["Required"]:
00650                         return "LEFT"
00651                 else:
00652                         return "RIGHT"
00653         cnt = 0
00654         ifType = {"--service": "Provided", "--consumer": "Required"}
00655         for opt, arg in opts:
00656                 if opt == "--service" or opt == "--consumer":
00657                         try:
00658                                 arg = re.sub("::", "@@", arg)
00659                                 portname, name, type = arg.split(":")
00660                                 portname = re.sub("@@", "::", portname)
00661                                 name     = re.sub("@@", "::", name)
00662                                 type     = re.sub("@@", "::", type)
00663                         except:
00664                                 sys.stderr.write("Invalid option: " \
00665                                                  + opt \
00666                                                  + "=" \
00667                                                  + arg)
00668                         port = findport(prof_list, portname)
00669                         if port == None:
00670                                 port = copy.deepcopy(prof)
00671                                 port["name"] = portname
00672                                 prof_list.append(port)
00673                                 
00674                         tmp = copy.deepcopy(ifprof)
00675                         tmp["name"] = name
00676                         tmp["type"] = type
00677                         tmp["direction"] = ifType[opt]
00678                         tmp["varname"] = name
00679                         tmp["instanceName"] = name
00680                         idlfname = FindIdlFile(opts, type)
00681                         if idlfname == None:
00682                                 print "Error:"
00683                                 print "IDL file not found for a interface: ", type
00684                                 sys.exit(1)
00685                         tmp["idlFile"] = idlfname
00686                         port["serviceInterface"].append(tmp)
00687                         port["rtcExt::position"] = lr(port)
00688                         cnt += 1
00689         return prof_list
00690 
00691 
00692 def FindIdlFile(opts, ifname):
00693         _re_text = "interface\s+" + ifname
00694         for opt, arg in opts:
00695                 if opt == "--service-idl" or opt == "--consumer-idl":
00696                         fname = arg
00697                         fd = open(fname, "r")
00698                         if fd == None:
00699                                 print "IDL file not found: ", arg
00700                                 sys.exit(1)
00701                         t = fd.read()
00702                         if None != re.compile(_re_text).search(t):
00703                                 fd.close()
00704                                 return fname
00705                         fd.close()
00706         return None
00707 
00708 def PickupIDLFiles(dict):
00709         svcidls = {}
00710         cnsidls = {}
00711         for svc in dict["servicePorts"]:
00712                 for sif in svc["serviceInterface"]:
00713                         if sif["direction"] == "Provided":
00714                                 svcidls[sif["idlFile"]] = ""
00715                         elif sif["direction"] == "Required":
00716                                 if not svcidls.has_key(sif["idlFile"]):
00717                                         cnsidls[sif["idlFile"]] = ""
00718         dict["service_idl"] = []
00719         dict["consumer_idl"] = []
00720         for f in svcidls.keys():
00721                 idl = {}
00722                 idl["idl_fname"] = f
00723                 idl["idl_basename"] = f.split(".")[0]
00724                 dict["service_idl"].append(idl)
00725         for f in cnsidls.keys():
00726                 idl = {}
00727                 idl["idl_fname"] = f
00728                 idl["idl_basename"] = f.split(".")[0]
00729                 dict["consumer_idl"].append(idl)
00730         return
00731 
00732 def CreateId(dict):
00733         dict["id"] = "RTC:" + \
00734             dict["basicInfo"]["vendor"] + "." + \
00735             dict["basicInfo"]["category"] + "." + \
00736             dict["basicInfo"]["name"] + ":" + \
00737             dict["basicInfo"]["version"]
00738 
00739 def find_opt(opts, value, default):
00740         for opt, arg in opts:
00741                 if opt.find(value) == 0:
00742                         return arg
00743 
00744         return default
00745 
00746 
00747 def find_opt_list(opts, value, default):
00748         list = []
00749         if len(default) > 0:
00750                 list += default
00751         for opt, arg in opts:
00752                 if opt == ("--" + value):
00753                         list.append(arg)
00754         return list
00755 
00756 
00757 class Backend:
00758         def __init__(self, mod_name, mod):
00759                 self.mod = mod
00760                 self.obj = getattr(mod, mod_name)
00761                 self.mod_name = mod_name
00762 
00763 
00764 class BackendLoader:
00765         def __init__(self):
00766                 self.backends = {}
00767                 self.opts = []
00768                 self.available()
00769                 return
00770                 
00771 
00772         def available(self):
00773                 path_list = [pyhelper_path, "."]
00774                 for path in path_list:
00775                         for f in os.listdir(path):
00776                                 if re.compile("_gen.py$").search(f):
00777                                         mod_name = f.replace(".py", "")
00778                                         opt_name = f.replace("_gen.py", "")
00779                                         mod = __import__(mod_name, globals(), locals(), [])
00780                                         try:
00781                                                 mod.usage()
00782                                                 be = Backend(mod_name, mod)
00783                                                 self.backends[opt_name] = be
00784                                         except:
00785                                                 pass
00786 
00787                 return self.backends
00788 
00789 
00790         def check_args(self, args):
00791                 for opt in args:
00792                         if opt.find('-b') == 0:
00793                                 backend_name = opt.replace("-b", "")
00794                                 if self.backends.has_key(backend_name):
00795                                         self.opts.append(backend_name)
00796                                 else:
00797                                         print "No such backend: ", backend_name
00798                                         sys.exit(-1)
00799                         elif opt.find('--backend=') == 0:
00800                                 backend_name = opt.replace("--backend=", "")
00801                                 if self.backends.has_key(backend_name):
00802                                         self.opts.append(backend_name)
00803                                 else:
00804                                         print "No such backend: ", backend_name
00805                                         sys.exit(-1)
00806                 return self.opts
00807 
00808 
00809         def get_opt_fmts(self):
00810                 fmts = []
00811                 for be in self.opts:
00812                         fmts += self.backends[be].mod.get_opt_fmt()
00813                 return fmts
00814 
00815 
00816         def usage_available(self):
00817                 print "The following backends are available."
00818                 space = 10
00819                 for key in self.backends:
00820                         desc = self.backends[key].mod.description()                     
00821                         print "    -b" + key + ("." * (space - len(key))) + desc
00822                 print """
00823 Backend [xxx] specific help can be available by the following options.
00824     -bxxx --help|-h or --backend=xxx --help|-h
00825         """
00826                 return
00827 
00828 
00829         def usage(self):
00830                 for be in self.opts:
00831                         print self.backends[be].mod.usage()                     
00832                         print ""
00833                 return
00834 
00835         def usage_short(self):
00836                 for be in self.opts:
00837                         print self.backends[be].mod.usage_short()
00838                         print ""
00839                 return
00840 
00841 
00842         def generate_code(self, data, opts):
00843                 for be in self.opts:
00844                         self.backends[be].obj(data, opts).print_all()
00845                 return
00846                 
00847 
00848 def fmtd_args(width, args):
00849         arg_fmt = [""]
00850         w = 0
00851         line = 0
00852         for a in args:
00853                 w += len(a) + 1
00854                 if w > width:
00855                         w = len(a) + 1
00856                         line += 1
00857                         arg_fmt.append("")
00858                 arg_fmt[line] += a + " "
00859         return arg_fmt
00860 
00861 
00862 
00863 def main():
00864         global opt_args_fmt
00865 
00866         backends = BackendLoader()
00867         backends.check_args(sys.argv[1:])
00868         opt_args_fmt += backends.get_opt_fmts()
00869 
00870         try:
00871                 opts, args = getopt.getopt(sys.argv[1:], "b:ho:v", opt_args_fmt)
00872         except getopt.GetoptError:
00873                 print "Error: Invalid option.", getopt.GetoptError
00874                 usage_short()
00875                 backends.usage_available()
00876                 sys.exit(-1)
00877 
00878         if not opts:
00879                 usage_short()
00880                 backends.usage_available()
00881                 sys.exit(-1)
00882 
00883         output = None
00884         verbose = False
00885         output_cxx = False
00886         output_python = False
00887 
00888         for o, a in opts:
00889                 if o == "-v":
00890                         verbose = True
00891                 if o in ("-h"):
00892                         usage_short()
00893                         backends.usage_available()
00894                         backends.usage_short()
00895                         sys.exit(0)
00896                 if o in ("--help"):
00897                         usage()
00898                         backends.usage_available()
00899                         backends.usage()
00900                         sys.exit(0)
00901                 if o in ("-o", "--output"):
00902                         output = a
00903                         # ...
00904 
00905         prefix = os.popen("rtm-config --prefix", "r").read().split("\n")
00906         idl_inc = []
00907         if prefix[0] != '':
00908                 idl_inc.append(prefix[0] + "/include/rtm/idl")
00909                 idl_inc.append(prefix[0] + "/include/rtm")
00910         idl_inc.append(".")
00911 
00912         # Create dictionary for ezt
00913         data = {'basicInfo':        CreateBasicInfo(opts),
00914                 'actions':          CreateActions(opts),
00915                 'configurationSet': CreateConfigurationSet(opts),
00916                 'dataPorts':        CreateDataPorts(opts),
00917                 'servicePorts':     CreateServicePorts(opts),
00918                 'args':             sys.argv,
00919                 'fmtd_args':        fmtd_args(70, sys.argv),
00920                 'idl_include':      idl_inc
00921                 }
00922         CreateId(data)
00923         PickupIDLFiles(data)
00924 
00925         if not data.has_key('fname'):
00926                 data['fname'] = data['basicInfo']['name']
00927         backends.generate_code(data, opts)
00928 
00929         import README_gen
00930         readme = README_gen.README_gen(data)
00931         readme.print_all()
00932         import profile_gen
00933         profile = profile_gen.profile_gen(data)
00934         profile.print_all()
00935         return
00936         
00937 
00938 if __name__ == "__main__":
00939         main()


openhrp3
Author(s): AIST, General Robotix Inc., Nakamura Lab of Dept. of Mechano Informatics at University of Tokyo
autogenerated on Thu Apr 11 2019 03:30:19