Esempio n. 1
0
    def __init__(self):
        if sys.platform.startswith("win"):
            self.dwf = cdll.dwf
        elif sys.platform.startswith("darwin"):
            self.dwf = cdll.LoadLibrary(
                "/Library/Frameworks/dwf.framework/dwf")
        elif sys.platform.startswith("cygwin"):
            self.dwf = CDLL("dwf.dll")
        else:
            self.dwf = cdll.LoadLibrary("libdwf.so")

        self.hdwf = c_int()

        v = create_string_buffer(16)
        self.dwf.FDwfGetVersion(v)
        self.dwfversion = v.value

        self.open()

        self._vposSetOffset = 0.0
        self._vposGetOffset = 0.0

        self.vpos = PowerSupply.PowerSupply(self.dwf, self.hdwf, 0)
        self.vneg = PowerSupply.PowerSupply(self.dwf, self.hdwf, 1)

        self.fg1 = FunctionGenerator.FunctionGenerator(self.dwf, self.hdwf, 0)
        self.fg2 = FunctionGenerator.FunctionGenerator(self.dwf, self.hdwf, 1)

        self.scope = Oscilloscope.Oscilloscope(self.dwf, self.hdwf)

        self.dwf.FDwfAnalogIOEnableSet(self.hdwf, c_int(True))
        self.dwf.FDwfDeviceAutoConfigureSet(self.hdwf, c_int(True))
Esempio n. 2
0
    def test_generateLogFunctions(self):
        self.maxDiff = None
        fg = FunctionGenerator()

        fmtStr = "Hello World! %0u %*.*s %*.19lf %19.*s"
        ret = fg.generateLogFunctions("ERROR", fmtStr, "testFile.cc",
                                            "testFile.cc", 100)
        logId = generateLogIdStr(fmtStr, "testFile.cc", 100)
        expectedFnName = "__syang0__fl" + logId

        expectedResult = ("void " + expectedFnName + "(NanoLog::LogLevel level"
                            ", const char* fmtStr , unsigned int arg0, "
                            "int arg1, int arg2, const char* arg3, "
                            "int arg4, double arg5, "
                            "int arg6, const char* arg7)",
                            expectedFnName)

        self.assertEqual(expectedResult, ret)

        self.assertEqual(2, len(fg.logId2Code))
        code = fg.logId2Code[logId]

        self.assertEqual(fmtStr, code["fmtString"])
        self.assertEqual("testFile.cc", code["filename"])
        self.assertEqual(100, code["linenum"])
Esempio n. 3
0
    def test_outputMappingFile(self):
        fg = FunctionGenerator()

        fg.generateLogFunctions("DEBUG", "A", "mar.cc", "mar.cc", 293)
        fg.generateLogFunctions("DEBUG", "B", "mar.cc", "mar.cc", 294)
        fg.generateLogFunctions("DEBUG", "C", "mar.cc", "mar.cc", 200)
        fg.generateLogFunctions("DEBUG", "D %d", "s.cc", "s.cc", 100)

        # Test serialization and deserialization
        fg.outputMappingFile("test.json")
        with open("test.json") as dataFile:
            data = json.load(dataFile)
            self.assertEqual(fg.argLists2Cnt, data.get('argLists2Cnt'))
            self.assertEqual(fg.logId2Code, data.get('logId2Code'))

        os.remove("test.json")
Esempio n. 4
0
    def test_generateLogFunctions_empty(self):
        self.maxDiff = None
        fg = FunctionGenerator()

        ret = fg.generateLogFunctions("DEBUG", "Empty Print", "gar.cc",
                                        "mar.cc", 293)

        logId = generateLogIdStr("Empty Print", "mar.cc", 293)
        expectedFnName = "__syang0__fl" + logId
        expectedResult = ("void " + expectedFnName + "(NanoLog::LogLevel level"
                                ", const char* fmtStr )", expectedFnName)
        self.assertEqual(expectedResult, ret)

        code = fg.logId2Code[logId]
        self.assertEqual("Empty Print", code['fmtString'])
        self.assertEqual("mar.cc", code["filename"])
        self.assertEqual(293, code["linenum"])
        self.assertEqual("gar.cc", code["compilationUnit"])
Esempio n. 5
0
    def test_outputMappingFile_withFolders(self):
        fg = FunctionGenerator()

        fg.generateLogFunctions("DEBUG", "A", "mar.cc", "mar.cc", 293)
        fg.generateLogFunctions("DEBUG", "B", "mar.cc", "mar.cc", 294)
        fg.generateLogFunctions("DEBUG", "C", "mar.cc", "mar.cc", 200)
        fg.generateLogFunctions("DEBUG", "D %d", "s.cc", "s.cc", 100)

        # Test what happens when the directory does not exist
        try:
            os.remove("testFolder/test.json")
            os.removedirs("testFolder")
        except:
            pass

        fg.outputMappingFile("testFolder/test.json")
        with open("testFolder/test.json") as dataFile:
            data = json.load(dataFile)
            self.assertEqual(fg.argLists2Cnt, data.get('argLists2Cnt'))
            self.assertEqual(fg.logId2Code, data.get('logId2Code'))

        os.remove("testFolder/test.json")
        os.removedirs("testFolder")
Esempio n. 6
0
    def test_outputCompilationFiles(self):
        self.maxDiff = None
        fg = FunctionGenerator()

        fg.generateLogFunctions("DEBUG", "A", "mar.cc", "mar.cc", 293)
        fg.generateLogFunctions("DEBUG", "B", "mar.cc", "mar.cc", 294)
        fg.generateLogFunctions("DEBUG", "C", "mar.cc", "mar.cc", 200)
        fg.generateLogFunctions("DEBUG", "D %d", "s.cc", "s.cc", 100)
        fg.generateLogFunctions("DEBUG", "E %4s %*.*lf", "s.cc", "s.cc", 100)

        fg.outputMappingFile("map1.map")

        # Also test the merging
        fg2 = FunctionGenerator()
        fg2.generateLogFunctions("DEBUG", "A", "mar.cc", "mar.cc", 293)
        fg2.generateLogFunctions("DEBUG", "A", "mar.cc", "mar.h", 1)
        fg2.generateLogFunctions("DEBUG", "E", "del.cc", "del.cc", 199)

        fg2.outputMappingFile("map2.map")
        # Merge the two map files
        FunctionGenerator.outputCompilationFiles("test.h",
                                                 ["map1.map", "map2.map"])

        self.assertTrue(filecmp.cmp("test.h",
                                "unitTestData/test_outputCompilationFiles.h"))

        os.remove("map1.map")
        os.remove("map2.map")
        os.remove("test.h")
Esempio n. 7
0
    def test_getRecordFunctionDefinitionsFor(self):
        self.maxDiff = None

        emptyRec = \
"""
inline void __syang0__fl{logId}(NanoLog::LogLevel level, const char* fmtStr ) {{
    extern const uint32_t __fmtId{logId};

    if (level > NanoLog::getLogLevel())
        return;

    uint64_t timestamp = PerfUtils::Cycles::rdtsc();
    ;
    size_t allocSize =   sizeof(NanoLogInternal::Log::UncompressedEntry);
    NanoLogInternal::Log::UncompressedEntry *re = reinterpret_cast<NanoLogInternal::Log::UncompressedEntry*>(NanoLogInternal::RuntimeLogger::reserveAlloc(allocSize));

    re->fmtId = __fmtId{logId};
    re->timestamp = timestamp;
    re->entrySize = static_cast<uint32_t>(allocSize);

    char *buffer = re->argData;

    // Record the non-string arguments
    %s

    // Record the strings (if any) at the end of the entry
    %s

    // Make the entry visible
    NanoLogInternal::RuntimeLogger::finishAlloc(allocSize);
}}
""" % ("", "")
        fg = FunctionGenerator()

        fg.generateLogFunctions("DEBUG", "A", "mar.cc", "mar.cc", 293)
        fg.generateLogFunctions("DEBUG", "B", "mar.cc", "mar.cc", 293)
        fg.generateLogFunctions("DEBUG", "C", "mar.cc", "mar.cc", 200)
        fg.generateLogFunctions("DEBUG", "D", "s.cc", "mar.cc", 100)

        self.assertEqual(3, len(fg.getRecordFunctionDefinitionsFor("mar.cc")))
        self.assertEqual(1, len(fg.getRecordFunctionDefinitionsFor("s.cc")))
        self.assertEqual(0, len(fg.getRecordFunctionDefinitionsFor("asdf.cc")))

        funcs = fg.getRecordFunctionDefinitionsFor("mar.cc")
        funcs.sort()

        logId = generateLogIdStr("A", "mar.cc", 293)
        self.assertMultiLineEqual(emptyRec.format(logId=logId), funcs[0])

        logId = generateLogIdStr("B", "mar.cc", 293)
        self.assertMultiLineEqual(emptyRec.format(logId=logId), funcs[1])

        logId = generateLogIdStr("C", "mar.cc", 200)
        self.assertMultiLineEqual(emptyRec.format(logId=logId), funcs[2])

        logId = generateLogIdStr("D", "mar.cc", 100)
        self.assertMultiLineEqual(emptyRec.format(logId=logId),
                                fg.getRecordFunctionDefinitionsFor("s.cc")[0])
Esempio n. 8
0
    def test_generateLogFunctions_combinationAndOverwrite(self):
        fg = FunctionGenerator()

        # TODO(syang0) Currently we do not differenciate on files, only strings.
        # In the future, please add multi-file support that way the correct
        # filename and line number are saved

        # Original
        fg.generateLogFunctions("DEBUG", "A", "mar.cc", "mar.cc", 293)

        # Different log
        fg.generateLogFunctions("DEBUG", "B", "mar.cc", "mar.cc", 293)

        # Same log + file, different location
        fg.generateLogFunctions("DEBUG", "A", "mar.cc",  "mar.cc", 200)

        # same log, diff file + location
        fg.generateLogFunctions("DEBUG", "A", "s.cc", "s.cc", 100)

        # same log, diff compilation unit, but same originating file
        fg.generateLogFunctions("DEBUG", "A", "s.cc", "mar.cc", 293)

        ids = list(fg.logId2Code)
        ids.sort()
        self.assertEqual(['__A__mar46cc__200__',
                          '__A__mar46cc__293__',
                          '__A__s46cc__100__',
                          '__B__mar46cc__293__',
                          '__INVALID__INVALID__INVALID__'], ids)
Esempio n. 9
0
def processFile(inputFile, mapOutputFilename):
    functionGenerator = FunctionGenerator()
    directiveRegex = re.compile("^# (\d+) \"(.*)\"(.*)")

    with open(inputFile) as f, open(inputFile + "i", 'w') as output:
        try:
            lines = f.readlines()
            lineIndex = -1

            lastChar = '\0'

            # Logical location in a file based on GNU Preprocessor directives
            ppFileName = inputFile
            ppLineNum = 0

            # Notes the first filename referenced by the pre-processor directives
            # which should be the name of the file being compiled.
            firstFilename = None

            # Marks at which line the preprocessor can start safely injecting
            # generated, inlined code. A value of None indicates that the NanoLog
            # header was not #include-d yet
            inlineCodeInjectionLineIndex = None

            # Scan through the lines of the file parsing the preprocessor directives,
            # identfying log statements, and replacing them with generated code.
            while lineIndex < len(lines) - 1:
                lineIndex = lineIndex + 1
                line = lines[lineIndex]

                # Keep track of of the preprocessor line number so that we can
                # put in our own line markers as we inject code into the file
                # and report errors. This line number should correspond to the
                # actual user source line number.
                ppLineNum = ppLineNum + 1

                # Parse special preprocessor directives that follows the format
                # '# lineNumber "filename" flags'
                if line[0] == "#":
                    directive = directiveRegex.match(line)
                    if directive:
                        # -1 since the line num describes the line after it, not the
                        # current one, so we decrement it here before looping
                        ppLineNum = int(float(directive.group(1))) - 1

                        ppFileName = directive.group(2)
                        if not firstFilename:
                            firstFilename = ppFileName

                        flags = directive.group(3).strip()
                        continue

                if INJECTION_MARKER in line:
                    inlineCodeInjectionLineIndex = lineIndex
                    continue

                if ppFileName in ignored_files:
                    continue

                # Scan for instances of the LOG_FUNCTION using a simple heuristic,
                # which is to search for the LOG_FUNCTION outside of quotes. This
                # works because at this point, the file should already be pre-processed
                # by the C/C++ preprocessor so all the comments have been stripped and
                # all #define's have been resolved.
                prevWasEscape = False
                inQuotes = False
                charOffset = -1

                # Optimization: Make sure line has LOG_FUNCTION before doing more work
                if LOG_FUNCTION not in line:
                    continue

                while charOffset < len(line) - 1:
                    charOffset = charOffset + 1
                    c = line[charOffset]

                    # If escape, we don't really care about the next char
                    if c == "\\" or prevWasEscape:
                        prevWasEscape = not prevWasEscape
                        lastChar = c
                        continue

                    if c == "\"":
                        inQuotes = not inQuotes

                    # If we match the first character, cheat a little and scan forward
                    if c == LOG_FUNCTION[0] and not inQuotes:
                        # Check if we've found the log function via the following heuristics
                        #  (a) the next n-1 characters spell out the rest of LOG_FUNCTION
                        #  (b) the previous character was not an alpha numeric (i.e. not
                        #       a part of a longer identifier name)
                        #  (c) the next syntactical character after log function is a (
                        found = True
                        for ii in range(len(LOG_FUNCTION)):
                            if line[charOffset + ii] != LOG_FUNCTION[ii]:
                                found = False
                                break

                        if not found:
                            continue

                        # Valid identifier characters are [a-zA-Z_][a-zA-Z0-9_]*
                        if lastChar.isalnum() or lastChar == '_':
                            continue

                        # Check that it's a function invocation via the existence of (
                        filePosAfter = FilePosition(
                            lineIndex, charOffset + len(LOG_FUNCTION))
                        mChar, mPos = peekNextMeaningfulChar(
                            lines, filePosAfter)
                        if mChar != "(":
                            continue

                        # Okay at this point we are pretty sure we have a genuine
                        # log statement, parse it and start modifying the code!
                        logStatement = parseLogStatement(
                            lines, (lineIndex, charOffset))
                        lastLogStatementLine = logStatement[
                            'semiColonPos'].lineNum

                        if len(logStatement['arguments']) < 2:
                            raise ValueError(
                                "NANO_LOG statement expects at least 2 arguments"
                                ": a LogLevel and a literal format string",
                                lines[lineIndex:lastLogStatementLine + 1])

                        # We expect the log invocation to have the following format:
                        # LOG_FN(LogLevel, FormatString, ...), hence the magic indexes
                        logLevel = logStatement['arguments'][0].source
                        fmtArg = logStatement['arguments'][1]
                        fmtString = extractCString(fmtArg.source)

                        # At this point, we should check that NanoLog was #include-d
                        # and that the format string was a static string
                        if not inlineCodeInjectionLineIndex:
                            raise ValueError(
                                "NANO_LOG statement occurred before "
                                "#include-ing the NanoLog header!",
                                lines[lineIndex:lastLogStatementLine + 1])

                        if not fmtString:
                            raise ValueError(
                                "NANO_LOG statement expects a literal format "
                                "string for its second argument",
                                lines[lineIndex:lastLogStatementLine + 1])

                        # Invoke the FunctionGenerator and if it throws a ValueError,
                        # tack on an extra argument to print out the log function itself
                        try:
                            (recordDecl, recordFn
                             ) = functionGenerator.generateLogFunctions(
                                 logLevel, fmtString, firstFilename,
                                 ppFileName, ppLineNum)
                        except ValueError as e:
                            raise ValueError(
                                e.args[0],
                                lines[lineIndex:lastLogStatementLine + 1])

                        # Now we're ready to inject the code. What's going to happen is
                        # that the original LOG_FUNCTION will be ripped out and in its
                        # place, a function invocation for the record logic will be
                        # inserted. It will look something like this:
                        #
                        #    input: "++i; LOG("Test, %d", 5); ++i;"
                        #    output: "i++;
                        #             # 1 "injectedCode.fake"
                        #             {
                        #             __syang0__fl__(
                        #             # 10 "original.cc"
                        #                     "Test, %d", 5); }
                        #             # 10 "original.cc"
                        #                                     ++i;"
                        #
                        # Note that we try to preserve spacing and use line preprocessor
                        # directives wherever we can so that if the compiler reports
                        # errors, then the errors can be consistent with the user's view
                        # of the source file.

                        # First we separate the code that comes after the log statement's
                        # semicolon onto its own line while preserving the line spacing
                        # and symbolic reference to the original source file
                        #
                        # Example:
                        #       "functionA(); functionB();"
                        # becomes
                        #       "functionA();
                        #       # 10 "filename.cc"
                        #                     functionB();"
                        #
                        # Note that we're working from back to front so that our line
                        # indices don't shift as we insert new lines.
                        scLineNum, scOffset = logStatement['semiColonPos']
                        scLine = lines[scLineNum]

                        # Extrapolate the symbolic line number
                        scPPLineNum = ppLineNum + (scLineNum - lineIndex)

                        # Split the line
                        scHeadLine = scLine[:scOffset + 1] + "\r\n"
                        scMarker = "# %d \"%s\"\r\n" % (scPPLineNum,
                                                        ppFileName)
                        scTailLine = " " * (scOffset + 1) + scLine[scOffset +
                                                                   1:]

                        lines[scLineNum] = scHeadLine
                        lines.insert(scLineNum + 1, scMarker)
                        lines.insert(scLineNum + 2, scTailLine)

                        # update the line we're working with in case the we split it above
                        if scLineNum == lineIndex:
                            line = lines[lineIndex]

                        # Next, we're going to replace the LOG_FUNCTION string from the
                        # first line with our generated function's name and insert
                        # the appropriate preprocessor directives to mark the boundaries
                        #
                        # Example:
                        #       "A(); LOG("Hello!);"
                        # Becomes
                        #       "A();
                        #        # 10 "injectedCode.fake"
                        #        { GENERATED_FUNC_NAME
                        #        # 10 "filename.cc"
                        #                ("Hello!");
                        #        }
                        #        # 10 "filename.cc"

                        # Close off the new scope
                        lines.insert(scLineNum + 1, "}\r\n")

                        offsetAfterLogFn = (charOffset + len(LOG_FUNCTION))
                        headOfLine = line[:charOffset]
                        tailOfLine = line[offsetAfterLogFn:].rjust(len(line))

                        lines[lineIndex] = \
                                      headOfLine \
                                        + "\r\n# %d \"injectedCode.fake\"\r\n" % ppLineNum \
                                        + "{ " + recordFn \
                                        + "\r\n# %d \"%s\"\r\n" % (ppLineNum, ppFileName) \
                                        + tailOfLine

                    lastChar = c
        except ValueError as e:
            print "\r\n%s:%d: Error - %s\r\n\r\n%s\r\n" % (
                ppFileName, ppLineNum, e.args[0], "".join(e.args[1]))
            sys.exit(1)

        # Last step, retrieve the generated code and insert it at the end
        recFns = functionGenerator.getRecordFunctionDefinitionsFor(
            firstFilename)
        codeToInject = "\r\n\r\n# 1 \"generatedCode.h\" 3\r\n" \
                                  + "\r\n".join(recFns)

        if recFns:
            # Assert is okay here since this should have been caught the first time
            # we found NANO_LOG without a #include
            assert inlineCodeInjectionLineIndex
            lines.insert(inlineCodeInjectionLineIndex + 1, codeToInject)

        # Output all the lines
        for line in lines:
            output.write(line)

        output.close()
        functionGenerator.outputMappingFile(mapOutputFilename)
Esempio n. 10
0
import numpy as np
import matplotlib.pyplot as plt
from scipy import signal
from scipy.stats import norm
import EncodingSchemes as ES
import DecodingSchemes as DS
import FunctionGenerator as FG

if __name__ == '__main__':
    dt = 0.01
    T_max = 4
    time = np.arange(0, T_max, dt)

    S = list()
    S.append(
        FG.sum_of_sine_waves([2, -0.5, 0.75], [1.0, 3.0, 5.0], [0.0, 0.0, 0.0],
                             0.0, time))
    S.append(FG.sum_of_sine_waves([-0.25], [1.0], [0.0], 0.05, time))
    S.append(
        FG.sum_of_gaussian_wave([1, 0.5], [0.2, 0.75], [0.1, 0.1], 0.1, time))

    # tbr_factors = [1.005, 1.005, 1.005]

    # sf_thresholds = [0.35, 0.05, 0.35]

    # mw_thresholds = [0.325, 0.015, 0.225]
    # mw_window = [3, 3, 3]

    # for i in range(len(S)):

    #     spikes_TBR, threshold = ES.temporal_contrast(S[i], tbr_factors[i])
    #     signal_TBR = 2*DS.temporal_contrast(spikes_TBR, threshold)
 def __init__(self, function_generator_resource_name):
     self.fg = FunctionGenerator.Agilent_33220x(
         function_generator_resource_name)
     self.__init_fg()