示例#1
0
 def _handleGetReservedAddrInfoRequest(self, request):
     chipsLog.debug("Reserved Address Info transaction requested")
     # Response header is the request header but with the Info Code field changed to INFO_CODE_RESPONSE
     responseHeader = IPbusHeader.updateInfoCode(request.getHeader(), IPbusHeader.INFO_CODE_RESPONSE)
     responseHeader = IPbusHeader.updateWords(responseHeader, 2)
     # Returning zeros for the response body, as no real idea what else it should be.
     return TransactionElement.makeFromHeaderAndBody(responseHeader, [0,0])
示例#2
0
    def _handleReadRequest(self, request):
        requestHeader = request.getHeader()
        words = IPbusHeader.getWords(requestHeader)
        baseAddr = request.getBody()[0]
        chipsLog.debug("Read requested on Addr=0x" + uInt32HexStr(baseAddr))

        # Response header is the request header but with the Info Code field changed to INFO_CODE_RESPONSE
        responseHeader = IPbusHeader.updateInfoCode(
            requestHeader, IPbusHeader.INFO_CODE_RESPONSE)

        # The (baseAddr & 0xffffffff) forces baseAddr to be in unsigned form (i.e. 0xfffffffc, say, rather than -4)
        if (
                baseAddr & 0xffffffff
        ) == 0xffffffff:  # A read on this register is a Dummy Hardware Reset Request.
            chipsLog.info(
                "** Dummy Hardware reset request received! Zeroing all registers. **"
            )
            self._registers.clear()

        responseBody = []
        appendToResponseBody = responseBody.append  # This is for a speed optimisation

        for offset in range(words):
            currentReg = baseAddr + offset
            # Create these registers if they don't already exist.
            if currentReg not in self._registers:
                self._registers[currentReg] = 0
            appendToResponseBody(self._registers[currentReg])
        return TransactionElement.makeFromHeaderAndBody(
            responseHeader, responseBody)
示例#3
0
 def _handleGetReservedAddrInfoRequest(self, request):
     chipsLog.debug("Reserved Address Info transaction requested")
     # Response header is the request header but with the Info Code field changed to INFO_CODE_RESPONSE
     responseHeader = IPbusHeader.updateInfoCode(
         request.getHeader(), IPbusHeader.INFO_CODE_RESPONSE)
     responseHeader = IPbusHeader.updateWords(responseHeader, 2)
     # Returning zeros for the response body, as no real idea what else it should be.
     return TransactionElement.makeFromHeaderAndBody(responseHeader, [0, 0])
示例#4
0
    def _handleWriteRequest(self, request):
        requestHeader = request.getHeader()
        words = IPbusHeader.getWords(requestHeader)
        requestBody = request.getBody()
        baseAddr = requestBody[0]
        chipsLog.debug("Write requested on Addr=0x" + uInt32HexStr(baseAddr))

        # Response header is the request header but with the Info Code field changed to INFO_CODE_RESPONSE
        responseHeader = IPbusHeader.updateInfoCode(requestHeader, IPbusHeader.INFO_CODE_RESPONSE)

        for offset in range(words):
            currentReg = baseAddr + offset  
            self._registers[currentReg] = requestBody[offset + 1]
        return TransactionElement.makeFromHeaderAndBody(responseHeader)
示例#5
0
    def _handleWriteRequest(self, request):
        requestHeader = request.getHeader()
        words = IPbusHeader.getWords(requestHeader)
        requestBody = request.getBody()
        baseAddr = requestBody[0]
        chipsLog.debug("Write requested on Addr=0x" + uInt32HexStr(baseAddr))

        # Response header is the request header with direction bit changed
        responseHeader = IPbusHeader.updateDirection(requestHeader, 1)

        for offset in range(words):
            currentReg = baseAddr + offset  
            self._registers[currentReg] = requestBody[offset + 1]
        return TransactionElement.makeFromHeaderAndBody(responseHeader)
示例#6
0
    def _handleWriteRequest(self, request):
        requestHeader = request.getHeader()
        words = IPbusHeader.getWords(requestHeader)
        requestBody = request.getBody()
        baseAddr = requestBody[0]
        chipsLog.debug("Write requested on Addr=0x" + uInt32HexStr(baseAddr))

        # Response header is the request header but with the Info Code field changed to INFO_CODE_RESPONSE
        responseHeader = IPbusHeader.updateInfoCode(
            requestHeader, IPbusHeader.INFO_CODE_RESPONSE)

        for offset in range(words):
            currentReg = baseAddr + offset
            self._registers[currentReg] = requestBody[offset + 1]
        return TransactionElement.makeFromHeaderAndBody(responseHeader)
示例#7
0
    def _createWriteTransactionElement(self,
                                       addrTableItem,
                                       dataList,
                                       addrOffset=0,
                                       isFifo=False):
        """Returns a Write Request transaction element (i.e. unmasked/block write)

        addrTableItem:  The relevant address table item you want to perform the write transaction on.
        dataList:  The list of 32-bit numbers you want to write (the list size defines the write depth)
        addrOffset:  The offset on the address specified within the address table item, default is 0.
        isFifo: False gives a normal write transaction; True gives a non-incrementing write transaction (i.e. same addr many times).
        """
        for value in dataList:
            if not uInt32Compatible(value):
                raise ChipsException("Write transaction creation error: cannot create a write transaction with data " \
                                     "values (" + hex(value) +") that are not valid 32-bit unsigned integers!")

        typeId = IPbusHeader.TYPE_ID_WRITE
        if isFifo: typeId = IPbusHeader.TYPE_ID_NON_INCR_WRITE
        writeHeader = IPbusHeader.makeHeader(ChipsBusBase.IPBUS_PROTOCOL_VER,
                                             self._getTransactionId(),
                                             len(dataList), typeId,
                                             IPbusHeader.INFO_CODE_REQUEST)
        writeBody = [addrTableItem.getAddress() + addrOffset] + dataList
        return TransactionElement.makeFromHeaderAndBody(writeHeader, writeBody)
示例#8
0
 def _createByteOrderTransactionElement(self):
     """Returns a Byte-Order Request transaction element.
     
     Note: Byte-order transactions will always and exclusively have transactionId = 0.
     """
     byteOrderHeader = IPbusHeader.makeHeader(ChipsBusBase.IPBUS_PROTOCOL_VER, 0, 0, IPbusHeader.TYPE_ID_BYTE_ORDER, 0, 0)
     return TransactionElement.makeFromHeaderAndBody(byteOrderHeader)
示例#9
0
    def _handleFifoReadRequest(self, request):
        requestHeader = request.getHeader()
        words = IPbusHeader.getWords(requestHeader)
        fifoAddr = request.getBody()[0]
        chipsLog.debug("FIFO read requested on Addr=0x" + uInt32HexStr(fifoAddr))

        # Response header is the request header with direction bit changed
        responseHeader = IPbusHeader.updateDirection(requestHeader, 1)

        # Create the register if they don't already exist in our memory space
        if fifoAddr not in self._registers:
            self._registers[fifoAddr] = 0

        # Obviously we don't really have a FIFO, so we'll just have to return the value stored
        # at the FIFO's address many times...
        value = self._registers[fifoAddr]
        responseBody = [value for iReads in range(words)]
        return TransactionElement.makeFromHeaderAndBody(responseHeader, responseBody)
示例#10
0
    def _handleFifoReadRequest(self, request):
        requestHeader = request.getHeader()
        words = IPbusHeader.getWords(requestHeader)
        fifoAddr = request.getBody()[0]
        chipsLog.debug("FIFO read requested on Addr=0x" +
                       uInt32HexStr(fifoAddr))

        # Response header is the request header but with the Info Code field changed to INFO_CODE_RESPONSE
        responseHeader = IPbusHeader.updateInfoCode(
            requestHeader, IPbusHeader.INFO_CODE_RESPONSE)

        # Create the register if they don't already exist in our memory space
        if fifoAddr not in self._registers:
            self._registers[fifoAddr] = 0

        # Obviously we don't really have a FIFO, so we'll just have to return the value stored
        # at the FIFO's address many times...
        value = self._registers[fifoAddr]
        responseBody = [value for iReads in range(words)]
        return TransactionElement.makeFromHeaderAndBody(
            responseHeader, responseBody)
示例#11
0
    def _createReadTransactionElement(self, addrTableItem, readDepth = 1, addrOffset = 0, isFifo = False):
        """Returns a Read Request transaction element

        addrTableItem:  The relevant address table item you want to perform the write transaction on.
        readDepth:  The depth of the read; default is 1, which would be a single 32-bit register read.
        addrOffset:  The offset on the address specified within the address table item, default is 0.
        isFifo: False gives a normal read transaction; True gives a non-incrementing read transaction (i.e. same addr many times).
        """
        typeId = IPbusHeader.TYPE_ID_READ
        if isFifo: typeId = IPbusHeader.TYPE_ID_NON_INCR_READ
        readHeader = IPbusHeader.makeHeader(ChipsBusBase.IPBUS_PROTOCOL_VER, self._getTransactionId(), readDepth, typeId, IPbusHeader.INFO_CODE_REQUEST)
        readBody = [addrTableItem.getAddress() + addrOffset]
        return TransactionElement.makeFromHeaderAndBody(readHeader, readBody)
示例#12
0
 def _createReadTransactionElement(self, addrTableItem, readDepth = 1, addrOffset = 0, isFifo = False):
     """Returns a Read Request transaction element
     
     addrTableItem:  The relevant address table item you want to perform the write transaction on.
     readDepth:  The depth of the read; default is 1, which would be a single 32-bit register read. 
     addrOffset:  The offset on the address specified within the address table item, default is 0.
     isFifo: False gives a normal read transaction; True gives a non-incrementing read transaction (i.e. same addr many times).
     """
     typeId = IPbusHeader.TYPE_ID_READ
     if isFifo: typeId = IPbusHeader.TYPE_ID_NON_INCR_READ
     readHeader = IPbusHeader.makeHeader(ChipsBusBase.IPBUS_PROTOCOL_VER, self._getTransactionId(), readDepth, typeId, IPbusHeader.INFO_CODE_REQUEST)
     readBody = [addrTableItem.getAddress() + addrOffset]
     return TransactionElement.makeFromHeaderAndBody(readHeader, readBody)
示例#13
0
    def _handleReadRequest(self, request):
        requestHeader = request.getHeader()
        words = IPbusHeader.getWords(requestHeader)
        baseAddr = request.getBody()[0]
        chipsLog.debug("Read requested on Addr=0x" + uInt32HexStr(baseAddr))

        # Response header is the request header with direction bit changed
        responseHeader = IPbusHeader.updateDirection(requestHeader, 1)

        # The (baseAddr & 0xffffffff) forces baseAddr to be in unsigned form (i.e. 0xfffffffc, say, rather than -4)
        if (baseAddr & 0xffffffff) == 0xffffffff:  # A read on this register is a Dummy Hardware Reset Request.
            chipsLog.info("** Dummy Hardware reset request received! Zeroing all registers. **")
            self._registers.clear()
        
        responseBody = []
        appendToResponseBody = responseBody.append  # This is for a speed optimisation  
        
        for offset in range(words):
            currentReg = baseAddr + offset  
            # Create these registers if they don't already exist.
            if currentReg not in self._registers:
                self._registers[currentReg] = 0
            appendToResponseBody(self._registers[currentReg])
        return TransactionElement.makeFromHeaderAndBody(responseHeader, responseBody)
示例#14
0
    def _handleFifoWriteRequest(self, request):
        requestHeader = request.getHeader()
        requestBody = request.getBody()
        fifoAddr = requestBody[0]
        chipsLog.debug("FIFO write requested on Addr=0x" + uInt32HexStr(fifoAddr))

        # Response header is the request header with direction bit changed
        responseHeader = IPbusHeader.updateDirection(requestHeader, 1)

        # Obviously we don't really have a FIFO, we just have a single register at the address of the supposed
        # FIFO.  So, whatever the last value written into the FIFO is, this will be the value this register will
        # take.  We ignore all the previous "writes" to the FIFO.
        self._registers[fifoAddr] = requestBody[-1]

        return TransactionElement.makeFromHeaderAndBody(responseHeader)
示例#15
0
    def _handleReadModifyWriteSumRequest(self, request):
        requestBody = request.getBody()
        addr = requestBody[0]
        addend = requestBody[1]  # The value we add to the existing value
        chipsLog.debug("Read/Modify/Write-sum requested on Addr=0x" + uInt32HexStr(addr))
        
        # Create the register if it doesn't already exist.
        if addr not in self._registers: self._registers[addr] = 0
        
        updatedValue = (self._registers[addr] + addend) & 0xffffffff
        self._registers[addr] = updatedValue

        # Response header is the request header with direction bit changed
        responseHeader = IPbusHeader.updateDirection(request.getHeader(), 1)

        return TransactionElement.makeFromHeaderAndBody(responseHeader, [updatedValue])
示例#16
0
    def _handleFifoWriteRequest(self, request):
        requestHeader = request.getHeader()
        requestBody = request.getBody()
        fifoAddr = requestBody[0]
        chipsLog.debug("FIFO write requested on Addr=0x" +
                       uInt32HexStr(fifoAddr))

        # Response header is the request header but with the Info Code field changed to INFO_CODE_RESPONSE
        responseHeader = IPbusHeader.updateInfoCode(
            requestHeader, IPbusHeader.INFO_CODE_RESPONSE)

        # Obviously we don't really have a FIFO, we just have a single register at the address of the supposed
        # FIFO.  So, whatever the last value written into the FIFO is, this will be the value this register will
        # take.  We ignore all the previous "writes" to the FIFO.
        self._registers[fifoAddr] = requestBody[-1]

        return TransactionElement.makeFromHeaderAndBody(responseHeader)
示例#17
0
    def _handleReadModifyWriteBitsRequest(self, request):
        requestBody = request.getBody()
        addr = requestBody[0]
        andTerm = requestBody[1]  # The and term is the bitwise complement of the register mask (i.e. mask = ~andTerm)
        orTerm = requestBody[2]
        chipsLog.debug("Read/Modify/Write-bits requested on Addr=0x" + uInt32HexStr(addr))
        
        # Create the register if it doesn't already exist.
        if addr not in self._registers: self._registers[addr] = 0
        
        updatedValue = (self._registers[addr] & andTerm) | (orTerm)
        self._registers[addr] = updatedValue

        # Response header is the request header with direction bit changed
        responseHeader = IPbusHeader.updateDirection(request.getHeader(), 1)

        return TransactionElement.makeFromHeaderAndBody(responseHeader, [updatedValue])
示例#18
0
    def _createRMWBitsTransactionElement(self, addrTableItem, dataU32, addrOffset = 0):
        """Returns a Read/Modify/Write Bits Request transaction element (i.e. masked write)

        addrTableItem:  The relevant address table item you want to perform the RMWBits transaction on.
        dataU32:  The data (32 bits max, or equal in width to the bit-mask).
        addrOffset:  The offset on the address specified within the address table item, default is 0.
        """

        if not uInt32Compatible(dataU32):
            raise ChipsException("Read-Modify-Write Bits transaction creation error: cannot create a RMW-bits " \
                            "transaction with data values (" + hex(dataU32) +") that are not valid 32-bit " \
                            "unsigned integers!")

        rmwHeader = IPbusHeader.makeHeader(ChipsBus.IPBUS_PROTOCOL_VER, self._getTransactionId(), 1, IPbusHeader.TYPE_ID_RMW_BITS, IPbusHeader.INFO_CODE_REQUEST)
        rmwBody = [addrTableItem.getAddress() + addrOffset, \
                   uInt32BitFlip(addrTableItem.getMask()), \
                   addrTableItem.shiftDataToMask(dataU32)]
        return TransactionElement.makeFromHeaderAndBody(rmwHeader, rmwBody)
示例#19
0
    def _createWriteTransactionElement(self, addrTableItem, dataList, addrOffset = 0, isFifo = False):
        """Returns a Write Request transaction element (i.e. unmasked/block write)
        
        addrTableItem:  The relevant address table item you want to perform the write transaction on.
        dataList:  The list of 32-bit numbers you want to write (the list size defines the write depth) 
        addrOffset:  The offset on the address specified within the address table item, default is 0.
        isFifo: False gives a normal write transaction; True gives a non-incrementing write transaction (i.e. same addr many times).
        """
        for value in dataList:
            if not uInt32Compatible(value):
                raise ChipsException("Write transaction creation error: cannot create a write transaction with data " \
                                     "values (" + hex(value) +") that are not valid 32-bit unsigned integers!")

        typeId = IPbusHeader.TYPE_ID_WRITE
        if isFifo: typeId = IPbusHeader.TYPE_ID_NON_INCR_WRITE
        writeHeader = IPbusHeader.makeHeader(ChipsBusBase.IPBUS_PROTOCOL_VER, self._getTransactionId(), len(dataList), typeId, IPbusHeader.INFO_CODE_REQUEST)
        writeBody = [addrTableItem.getAddress() + addrOffset] + dataList
        return TransactionElement.makeFromHeaderAndBody(writeHeader, writeBody)
示例#20
0
 def _actAndRespond(self, transaction):
     """Performs the required action and returns the response for a given transaction"""
     self._transactionCounter += 1
     chipsLog.debug("*** Performing transaction #" + str(self._transactionCounter) + " ***")
     try:
         transaction.deserialiseRequests()
 
         for request in transaction.requests:
             transaction.appendResponse(self._requestTypeHandlerMap[IPbusHeader.getTypeId(request.getHeader())](request))
         
         transaction.serialiseResponses()
         chipsLog.debug("Sending response packet")
         self._socketSend(transaction)
         chipsLog.debug("Response packet sent!")
         chipsLog.debug("*** Transaction #" + str(self._transactionCounter) + " completed! ***\n")
     except ChipsException, err:
         chipsLog.error("ERROR! Transaction #" + str(self._transactionCounter) + 
                        " could not be successfully processed:\n\t" + str(err))
示例#21
0
    def _createRMWBitsTransactionElement(self, addrTableItem, dataU32, addrOffset = 0):
        """Returns a Read/Modify/Write Bits Request transaction element (i.e. masked write)
        
        addrTableItem:  The relevant address table item you want to perform the RMWBits transaction on.
        dataU32:  The data (32 bits max, or equal in width to the bit-mask).
        addrOffset:  The offset on the address specified within the address table item, default is 0.
        """

        if not uInt32Compatible(dataU32):
            raise ChipsException("Read-Modify-Write Bits transaction creation error: cannot create a RMW-bits " \
                            "transaction with data values (" + hex(dataU32) +") that are not valid 32-bit " \
                            "unsigned integers!")
    
        rmwHeader = IPbusHeader.makeHeader(ChipsBus.IPBUS_PROTOCOL_VER, self._getTransactionId(), 1, IPbusHeader.TYPE_ID_RMW_BITS, IPbusHeader.INFO_CODE_REQUEST)
        rmwBody = [addrTableItem.getAddress() + addrOffset, \
                   uInt32BitFlip(addrTableItem.getMask()), \
                   addrTableItem.shiftDataToMask(dataU32)]
        return TransactionElement.makeFromHeaderAndBody(rmwHeader, rmwBody)
示例#22
0
    def _handleReadModifyWriteSumRequest(self, request):
        requestBody = request.getBody()
        addr = requestBody[0]
        addend = requestBody[1]  # The value we add to the existing value
        chipsLog.debug("Read/Modify/Write-sum requested on Addr=0x" +
                       uInt32HexStr(addr))

        # Create the register if it doesn't already exist.
        if addr not in self._registers: self._registers[addr] = 0

        updatedValue = (self._registers[addr] + addend) & 0xffffffff
        self._registers[addr] = updatedValue

        # Response header is the request header but with the Info Code field changed to INFO_CODE_RESPONSE
        responseHeader = IPbusHeader.updateInfoCode(
            request.getHeader(), IPbusHeader.INFO_CODE_RESPONSE)

        return TransactionElement.makeFromHeaderAndBody(
            responseHeader, [updatedValue])
示例#23
0
    def _handleReadModifyWriteBitsRequest(self, request):
        requestBody = request.getBody()
        addr = requestBody[0]
        andTerm = requestBody[
            1]  # The and term is the bitwise complement of the register mask (i.e. mask = ~andTerm)
        orTerm = requestBody[2]
        chipsLog.debug("Read/Modify/Write-bits requested on Addr=0x" +
                       uInt32HexStr(addr))

        # Create the register if it doesn't already exist.
        if addr not in self._registers: self._registers[addr] = 0

        updatedValue = (self._registers[addr] & andTerm) | (orTerm)
        self._registers[addr] = updatedValue

        # Response header is the request header but with the Info Code field changed to INFO_CODE_RESPONSE
        responseHeader = IPbusHeader.updateInfoCode(
            request.getHeader(), IPbusHeader.INFO_CODE_RESPONSE)

        return TransactionElement.makeFromHeaderAndBody(
            responseHeader, [updatedValue])
示例#24
0
    def _actAndRespond(self, transaction):
        """Performs the required action and returns the response for a given transaction"""
        self._transactionCounter += 1
        chipsLog.debug("*** Performing transaction #" +
                       str(self._transactionCounter) + " ***")
        try:
            transaction.deserialiseRequests()

            for request in transaction.requests:
                transaction.appendResponse(
                    self._requestTypeHandlerMap[IPbusHeader.getTypeId(
                        request.getHeader())](request))

            transaction.serialiseResponses()
            chipsLog.debug("Sending response packet")
            self._socketSend(transaction)
            chipsLog.debug("Response packet sent!")
            chipsLog.debug("*** Transaction #" +
                           str(self._transactionCounter) + " completed! ***\n")
        except ChipsException, err:
            chipsLog.error("ERROR! Transaction #" +
                           str(self._transactionCounter) +
                           " could not be successfully processed:\n\t" +
                           str(err))
示例#25
0
 def _handleByteOrderRequest(self, request):
     chipsLog.debug("Byte-order transaction requested")
     # Response header is the request header with direction bit changed
     responseHeader = IPbusHeader.updateDirection(request.getHeader(), 1)
     return TransactionElement.makeFromHeaderAndBody(responseHeader)
示例#26
0
 def _handleGetReservedAddrInfoRequest(self, request):
     # Response header is the request header with direction bit changed
     responseHeader = IPbusHeader.updateDirection(request.getHeader(), 1)
     responseHeader = IPbusHeader.updateWords(responseHeader, 2)
     # Returning zeros for the response body, as no real idea what else it should be.
     return TransactionElement.makeFromHeaderAndBody(responseHeader, [0,0])
示例#27
0
 def validBodySize(self):
     '''Returns true/false if the current body size matches the size inferred by the header.'''
     return (len(self._rawData) - 1) == IPbusHeader.getExpectedBodySize(self.getHeader())
示例#28
0
 def validBodySize(self):
     """Returns true/false if the current body size matches the size inferred by the header."""
     return (len(self._rawData) - 1) == IPbusHeader.getExpectedBodySize(self.getHeader())