Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2026-04-09 07:48:47

0001 #!/usr/bin/env python
0002 #
0003 # Copyright (c) 2019 Opticks Team. All Rights Reserved.
0004 #
0005 # This file is part of Opticks
0006 # (see https://bitbucket.org/simoncblyth/opticks).
0007 #
0008 # Licensed under the Apache License, Version 2.0 (the "License");
0009 # you may not use this file except in compliance with the License.
0010 # You may obtain a copy of the License at
0011 #
0012 #   http://www.apache.org/licenses/LICENSE-2.0
0013 #
0014 # Unless required by applicable law or agreed to in writing, software
0015 # distributed under the License is distributed on an "AS IS" BASIS,
0016 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
0017 # See the License for the specific language governing permissions and
0018 # limitations under the License.
0019 #
0020 
0021 """
0022 enum_.py
0023 =================
0024 
0025 Canonical usage is for parsing SysRap/OpticksPhoton.h and SysRap/OpticksGenstep.h
0026 which is done from custom commands in optickscore/CMakeLists.txt
0027 
0028 Renaming to enum_ was required due to a py3 module name clash.
0029 
0030 Test this with::
0031 
0032    cd ~/opticks/sysrap ; ../ana/enum_.py OpticksGenstep.h --quiet --simple --inipath /tmp/OpticksGenstep_Enum.ini && cat /tmp/OpticksGenstep_Enum.ini
0033    cd ~/opticks/sysrap ; ../ana/enum_.py OpticksPhoton.h --quiet --inipath /tmp/OpticksPhoton_Enum.ini && cat /tmp/OpticksPhoton_Enum.ini
0034 
0035 The non-simple form is for parsing enum values of form "0x1 << 4"
0036 
0037 """
0038 import os, re, argparse
0039 import logging
0040 log = logging.getLogger(__name__)
0041 
0042 class Enum(dict):
0043     lptn = re.compile(r"^\s*(\w+)\s*=\s*(.*?),*\s*?$")
0044     vptn = re.compile(r"^0x1 <<\s*(\d+)$")
0045     END = "};"
0046 
0047     def __init__(self, path, mskval=True, simple=False, end=True):
0048         """
0049         :param path:
0050         :param mskval:
0051         :param simple: when True means plain int enum, ie not bitshifted 0x1 << 1 etc..
0052         """
0053         dict.__init__(self)
0054         log.debug("parsing %s " % path )
0055         path = os.path.expandvars(path)
0056         log.debug("path expands to %s " % path )
0057 
0058         self.end = end
0059 
0060         if simple:
0061             self.parse_simple(path)
0062         else:
0063             self.parse(path, mskval=mskval)
0064         pass
0065 
0066     def __repr__(self):
0067         return "\n".join([" %-2d : %s " % (kv[1], kv[0] ) for kv in sorted(self.items(), key=lambda kv:kv[1])])
0068 
0069     def _get_ini(self):
0070         return "\n".join(["%s=%s" % (kv[0], kv[1] ) for kv in sorted(self.items(), key=lambda kv:kv[1])])
0071     ini = property(_get_ini)
0072 
0073     def parse_simple(self, path):
0074         """
0075         """
0076         lines = list(map(str.strip,open(path,"r").readlines()))
0077         for line in lines:
0078             if self.end and line.startswith(self.END): break
0079             lm = self.lptn.match(line)
0080 
0081             if not lm: continue
0082             lg = lm.groups()
0083             assert len(lg) == 2
0084             label, val = lg
0085             self[label] = int(val)
0086         pass
0087 
0088     def parse(self, path, mskval=True):
0089         """
0090         :param path:
0091         :param mskval:
0092         """
0093         lines = list(map(str.strip,open(path,"r").readlines()))
0094         for line in lines:
0095             if self.end and line.startswith(self.END): break
0096             lm = self.lptn.match(line)
0097             if not lm: continue
0098 
0099             lg = lm.groups()
0100             assert len(lg) == 2
0101             label, val = lg
0102 
0103             vm = self.vptn.match(val)
0104             assert vm
0105             vg = vm.groups()
0106             assert len(vg) == 1
0107             n = int(vg[0])
0108 
0109             emsk = eval(val)
0110             msk = 0x1 << n
0111             assert emsk == msk
0112 
0113             log.debug( "%-40s     ==> [%s]    [%s]  ==> [%d] ==> [%x]  " % (line, label, val, n, msk) )
0114 
0115             self[label] = msk if mskval else n + 1   ## Q: WHY +1 ?
0116 
0117 
0118 if __name__ == '__main__':
0119 
0120     default_path = "$OPTICKS_PREFIX/include/SysRap/OpticksPhoton.h"
0121     ## NB envvar not needed when absolute path argument given
0122 
0123     parser = argparse.ArgumentParser(__doc__)
0124     parser.add_argument(     "path",  nargs="?", help="Path to input header", default=default_path )
0125     parser.add_argument(     "--inipath", default=None, help="When a path is provided an ini file will be written to it." )
0126     parser.add_argument(     "--quiet", action="store_true", default=False, help="Skip dumping" )
0127     parser.add_argument(     "--mskval", action="store_true", default=False, help="Store the mask value rather than the smaller power of two int" )
0128     parser.add_argument(     "--simple", action="store_true", default=False, help="Simple value enum without bit shifting for masks " )
0129     parser.add_argument(     "--level", default="info", help="logging level" )
0130     parser.add_argument(     "--noend", dest="end", default=True, action="store_false", help="inhibit ending of parse at END" )
0131     args = parser.parse_args()
0132 
0133     fmt = '[%(asctime)s] p%(process)s {%(pathname)s:%(lineno)d} %(levelname)s - %(message)s'
0134     logging.basicConfig(level=getattr(logging,args.level.upper()), format=fmt)
0135 
0136     if args.path == default_path:
0137         pass
0138         log.info("using default path %s " % args.path)
0139     else:
0140         pass
0141         log.info("using argument input path %s " % args.path)
0142     pass
0143 
0144     d = Enum(args.path, mskval=args.mskval, simple=args.simple, end=args.end)
0145 
0146     if not args.quiet:
0147         print(d)
0148         print(d.ini)
0149     pass
0150     if not args.inipath is None:
0151         log.info("writing ini to inipath %s " % args.inipath)
0152         open(args.inipath, "w").write(d.ini)
0153     pass
0154 
0155 
0156 
0157 
0158 
0159