plugger.py
changeset 22 9a0c535c3272
parent 20 d3cb5020997b
child 23 e007d9d466d7
equal deleted inserted replaced
21:bded6d31365c 22:9a0c535c3272
     5 import os,sys
     5 import os,sys
     6 import plugins
     6 import plugins
     7 import types
     7 import types
     8 import shutil
     8 import shutil
     9 from xml.dom import minidom
     9 from xml.dom import minidom
       
    10 import wx
    10 
    11 
    11 #Quick hack to be able to find Beremiz IEC tools. Should be config params.
    12 #Quick hack to be able to find Beremiz IEC tools. Should be config params.
    12 base_folder = os.path.split(sys.path[0])[0]
    13 base_folder = os.path.split(sys.path[0])[0]
    13 sys.path.append(os.path.join(base_folder, "plcopeneditor"))
    14 sys.path.append(os.path.join(base_folder, "plcopeneditor"))
    14 
    15 
   134     def PlugGenerate_C(self, buildpath, current_location, locations, logger):
   135     def PlugGenerate_C(self, buildpath, current_location, locations, logger):
   135         """
   136         """
   136         Generate C code
   137         Generate C code
   137         @param current_location: Tupple containing plugin IEC location : %I0.0.4.5 => (0,0,4,5)
   138         @param current_location: Tupple containing plugin IEC location : %I0.0.4.5 => (0,0,4,5)
   138         @param locations: List of complete variables locations \
   139         @param locations: List of complete variables locations \
   139             [(IEC_loc, IEC_Direction, IEC_Type, Name)]\
   140             [{"IEC_TYPE" : the IEC type (i.e. "INT", "STRING", ...)
   140             ex: [((0,0,4,5),'I','STRING','__IX_0_0_4_5'),...]
   141             "NAME" : name of the variable (generally "__IW0_1_2" style)
       
   142             "DIR" : direction "Q","I" or "M"
       
   143             "SIZE" : size "X", "B", "W", "D", "L"
       
   144             "LOC" : tuple of interger for IEC location (0,1,2,...)
       
   145             }, ...]
   141         @return: [(C_file_name, CFLAGS),...] , LDFLAGS_TO_APPEND
   146         @return: [(C_file_name, CFLAGS),...] , LDFLAGS_TO_APPEND
   142         """
   147         """
   143         logger.write_warning(".".join(map(lambda x:str(x), current_location)) + " -> Nothing yo do")
   148         logger.write_warning(".".join(map(lambda x:str(x), current_location)) + " -> Nothing yo do\n")
   144         return [],""
   149         return [],""
   145     
   150     
   146     def _Generate_C(self, buildpath, current_location, locations, logger):
   151     def _Generate_C(self, buildpath, current_location, locations, logger):
   147         # Generate plugins [(Cfiles, CFLAGS)], LDFLAGS
   152         # Generate plugins [(Cfiles, CFLAGS)], LDFLAGS
   148         PlugCFilesAndCFLAGS, PlugLDFLAGS = self.PlugGenerate_C(buildpath, current_location, locations, logger)
   153         PlugCFilesAndCFLAGS, PlugLDFLAGS = self.PlugGenerate_C(buildpath, current_location, locations, logger)
   156                     #keep the same path
   161                     #keep the same path
   157                     buildpath,
   162                     buildpath,
   158                     # but update location (add curent IEC channel at the end)
   163                     # but update location (add curent IEC channel at the end)
   159                     new_location,
   164                     new_location,
   160                     # filter locations that start with current IEC location
   165                     # filter locations that start with current IEC location
   161                     [ (l,d,t,n) for l,d,t,n in locations if l[0:len(new_location)] == new_location ],
   166                     [loc for loc in locations if loc["LOC"][0:len(new_location)] == new_location ],
   162                     #propagete logger
   167                     #propagete logger
   163                     logger)
   168                     logger)
   164             # stack the result
   169             # stack the result
   165             PlugCFilesAndCFLAGS += CFilesAndCFLAGS
   170             PlugCFilesAndCFLAGS += CFilesAndCFLAGS
   166             PlugLDFLAGS += LDFLAGS
   171             PlugLDFLAGS += LDFLAGS
   375 # import necessary stuff from PLCOpenEditor
   380 # import necessary stuff from PLCOpenEditor
   376 from PLCControler import PLCControler
   381 from PLCControler import PLCControler
   377 from PLCOpenEditor import PLCOpenEditor, ProjectDialog
   382 from PLCOpenEditor import PLCOpenEditor, ProjectDialog
   378 from TextViewer import TextViewer
   383 from TextViewer import TextViewer
   379 from plcopen.structures import IEC_KEYWORDS
   384 from plcopen.structures import IEC_KEYWORDS
       
   385 import re
   380 
   386 
   381 class PluginsRoot(PlugTemplate):
   387 class PluginsRoot(PlugTemplate):
   382     """
   388     """
   383     This class define Root object of the plugin tree. 
   389     This class define Root object of the plugin tree. 
   384     It is responsible of :
   390     It is responsible of :
   502             dialog.Destroy()
   508             dialog.Destroy()
   503             return "Project not created"
   509             return "Project not created"
   504         
   510         
   505         # Create Controler for PLCOpen program
   511         # Create Controler for PLCOpen program
   506         self.PLCManager = PLCControler()
   512         self.PLCManager = PLCControler()
   507         self.PLCManager.CreateNewProject(PLCParams.pop("projectName"))
   513         self.PLCManager.CreateNewProject(values.pop("projectName"))
   508         self.PLCManager.SetProjectProperties(properties = PLCParams)
   514         self.PLCManager.SetProjectProperties(properties = values)
   509         # Change XSD into class members
   515         # Change XSD into class members
   510         self._AddParamsMembers()
   516         self._AddParamsMembers()
   511         self.PluggedChilds = {}
   517         self.PluggedChilds = {}
   512         # Keep track of the root plugin (i.e. project path)
   518         # Keep track of the root plugin (i.e. project path)
   513         self.ProjectPath = ProjectPath
   519         self.ProjectPath = ProjectPath
   585         plc_file = self._getIECcodepath()
   591         plc_file = self._getIECcodepath()
   586         # ask PLCOpenEditor controller to write ST/IL/SFC code file
   592         # ask PLCOpenEditor controller to write ST/IL/SFC code file
   587         result = self.PLCManager.GenerateProgram(plc_file)
   593         result = self.PLCManager.GenerateProgram(plc_file)
   588         if not result:
   594         if not result:
   589             # Failed !
   595             # Failed !
   590             logger.write_error("Error : ST/IL/SFC code generator returned %d"%result)
   596             logger.write_error("Error : ST/IL/SFC code generator returned %d\n"%result)
   591             return False
   597             return False
   592         logger.write("Compiling ST Program in to C Program...\n")
   598         logger.write("Compiling ST Program in to C Program...\n")
   593         # Now compile IEC code into many C files
   599         # Now compile IEC code into many C files
   594         # files are listed to stdout, and errors to stderr. 
   600         # files are listed to stdout, and errors to stderr. 
   595         status, result, err_result = logger.LogCommand("%s %s -I %s %s"%(iec2cc_path, plc_file, ieclib_path, self.TargetDir))
   601         status, result, err_result = logger.LogCommand("%s %s -I %s %s"%(iec2cc_path, plc_file, ieclib_path, buildpath))
   596         if status:
   602         if status:
   597             # Failed !
   603             # Failed !
   598             logger.write_error("Error : IEC to C compiler returned %d"%status)
   604             logger.write_error("Error : IEC to C compiler returned %d\n"%status)
   599             return False
   605             return False
   600         # Now extract C files of stdout
   606         # Now extract C files of stdout
   601         C_files = result.splitlines()
   607         C_files = result.splitlines()
   602         # remove those that are not to be compiled because included by others
   608         # remove those that are not to be compiled because included by others
   603         C_files.remove("POUS.c")
   609         C_files.remove("POUS.c")
   639 
   645 
   640         # Eventually create build dir
   646         # Eventually create build dir
   641         if not os.path.exists(buildpath):
   647         if not os.path.exists(buildpath):
   642             os.mkdir(buildpath)
   648             os.mkdir(buildpath)
   643         
   649         
   644         logger.write("Start build in %s" % buildpath)
   650         logger.write("Start build in %s\n" % buildpath)
   645         
   651         
   646         # Generate SoftPLC code
   652         # Generate SoftPLC code
   647         if not self._Generate_SoftPLC(logger):
   653         if not self._Generate_SoftPLC(logger):
   648             logger.write_error("SoftPLC code generation failed !")
   654             logger.write_error("SoftPLC code generation failed !\n")
   649             return False
   655             return False
   650 
   656 
   651         logger.write("SoftPLC code generation successfull")
   657         logger.write("SoftPLC code generation successfull\n")
   652         
   658         
   653         # Generate C code and compilation params from plugin hierarchy
   659         # Generate C code and compilation params from plugin hierarchy
   654         try:
   660         try:
   655             CFilesAndCFLAGS, LDFLAGS = self._Generate_C(
   661             CFilesAndCFLAGS, LDFLAGS = self._Generate_C(
   656                 buildpath, 
   662                 buildpath, 
   657                 (), 
   663                 (), 
   658                 self.PLCGeneratedLocatedVars,
   664                 self.PLCGeneratedLocatedVars,
   659                 logger)
   665                 logger)
   660         except Exception, msg:
   666         except Exception, msg:
   661             logger.write_error("Plugins code generation Failed !")
   667             logger.write_error("Plugins code generation Failed !\n")
   662             logger.write_error(str(msg))
   668             logger.write_error(str(msg))
   663             return False
   669             return False
   664 
   670 
   665         logger.write_error("Plugins code generation successfull")
   671         logger.write("Plugins code generation successfull\n")
   666 
   672 
   667         # Compile the resulting code into object files.
   673         # Compile the resulting code into object files.
   668         for CFile, CFLAG in CFilesAndCFLAGS:
   674         for CFile, CFLAG in CFilesAndCFLAGS:
   669             print CFile,CFLAG
   675             logger.write(str((CFile,CFLAG)))
   670         
   676         
   671         # Link object files into something that can be executed on target
   677         # Link object files into something that can be executed on target
   672         print LDFLAGS
   678         logger.write(LDFLAGS)
   673 
   679 
   674     def _showIECcode(self, logger):
   680     def _showIECcode(self, logger):
   675         plc_file = self._getIECcodepath()
   681         plc_file = self._getIECcodepath()
   676         new_dialog = wx.Frame(None)
   682         new_dialog = wx.Frame(None)
   677         ST_viewer = TextViewer(new_dialog, None, None)
   683         ST_viewer = TextViewer(new_dialog, None, None)
   685             
   691             
   686         new_dialog.Show()
   692         new_dialog.Show()
   687 
   693 
   688     def _EditPLC(self, logger):
   694     def _EditPLC(self, logger):
   689         if not self.PLCEditor:
   695         if not self.PLCEditor:
   690             self.PLCEditor = PLCOpenEditor(self, self.PLCManager)
   696             self.PLCEditor = PLCOpenEditor(self.AppFrame, self.PLCManager)
   691             self.PLCEditor.RefreshProjectTree()
   697             self.PLCEditor.RefreshProjectTree()
   692             self.PLCEditor.RefreshFileMenu()
   698             self.PLCEditor.RefreshFileMenu()
   693             self.PLCEditor.RefreshEditMenu()
   699             self.PLCEditor.RefreshEditMenu()
   694             self.PLCEditor.RefreshToolBar()
   700             self.PLCEditor.RefreshToolBar()
   695             self.PLCEditor.Show()
   701             self.PLCEditor.Show()
   696 
   702 
   697     PluginMethods = [("Build",_build), ("Clean",None), ("Run",None), ("EditPLC",None), ("Show IEC code",_showIECcode)]
   703     def _Clean(self, logger):
   698     
   704         logger.write_error("Not impl\n")
       
   705     
       
   706     def _Run(self, logger):
       
   707         logger.write_error("Not impl\n")
       
   708 
       
   709     PluginMethods = [("EditPLC",_EditPLC), ("Build",_build), ("Clean",_Clean), ("Run",_Run), ("Show IEC code",_showIECcode)]
       
   710