# -*- coding: latin1 -*-
""" reptor.py - Event Replication for Adabas main module
"""
from __future__ import print_function # PY3
from adapya.base.defs import adalog as log
from adapya.adabas import adaerror
from adapya.era.urb import Urbc,Urbd,Urbe,Urbh,Urbi,Urbr
from adapya.era.urb import Urbs,Urbsu,Urbt,Urbu,Urbi_isns,New_Urb
from adapya.era.urb import Urbf,Urbg,URBFL,URBGL,URBFVER1,URBFEYE,urbfflag_str
from adapya.era.urb import URBHEYE,URBHL,URBHBORD,URBHVER1
from adapya.era.urb import URBCEYE,URBCL,URBDEYE,URBDL,urbd_type
from adapya.era.urb import URBEEYE,URBEL
from adapya.era.urb import URBIEYE,URBIL,URBIRTIS,URBIIRANGE,URBIIRANGELEN
from adapya.era.urb import URBIISNLEN,URBIRTTA,URBIRTST,URBIRTCD
from adapya.era.urb import URBREYE,URBRL,urbr_type
from adapya.era.urb import URBSEYE,URBSL,URBSSTAU
from adapya.era.urb import URBTEYE,URBTL,URBTRSNY,URBTINSY,URBTCONY
from adapya.era.urb import URBUEYE,URBUL
from adapya.era.urb import urbs_status
from adapya.era.urb import REPTOR_RSP,texts_reptor_subcodes
from adapya.base.dump import dump
from adapya.base import conv
from adapya.base import datamap
from adapya.base import ecscodec
from adapya.base import stck
import binascii
import types
try:
from adapya.era import xtra # external optional plugin
except:
xtra = None
fname=''
substat=None
[docs]class ReptorError(Exception): pass
[docs]class ParmsSubscription(object):
"defines parameters for updating the target database"
rblmax=0
fblmax=0
def __init__(self,subscription='',sversion='', sfiles=[]):
"""
subscription = name of subscription to handle
version = 2 byte version string compared with Reptor SVERSION
sfiles = list of ParmSubsFile objects
"""
self.subscription=subscription
self.sfiles=sfiles
if len(sfiles) > 0:
self.tdbid=sfiles[0].tdbid
for s in self.sfiles:
if s.dmap:
sz = s.dmap.getsize()
else:
sz = 0x7ff0
if ParmsSubscription.rblmax < sz:
ParmsSubscription.rblmax = sz
if ParmsSubscription.fblmax < len(s.fb):
ParmsSubscription.fblmax=len(s.fb)
if self.tdbid != s.tdbid:
raise ReptorError( 'Multiple target DBIDs not supported in subscription processing')
[docs]class ParmsSfile(object):
""" Defines parameters for updating the target database
source and target database/file parameters
and the record format
:param sdbid: source database id
:param sfnr: source file number
:param tdbid: target database id
:param tfnr: target file number
:param fb: format buffer when storing data
:param dmap: datamap object describing fields in record
"""
def __init__(self,fb='',dmap=None,handler=None,\
sdbid=0,sfnr=0,tdbid=0,tfnr=0):
self.sdbid=sdbid
self.sfnr=sfnr
self.tdbid=tdbid
self.tfnr=tfnr
self.fb=fb
self.handler=handler
self.dmap=dmap
if dmap:
self.rbl = dmap.getsize() # set size of datamap
else:
self.rbl = 0
[docs]class SubscriptionStatus(object):
"""Holds current processing status of message(s) received"""
snam=''
sdbid=0
sfnr=0
smap=None
typURBH = 1 # input type with URBH header (from Message Queue or ADARIS)
# set in ProcessingStatus().type with the first message
# create datamap objects for each structure
cc=Urbc(buffer=None,offset=0)
dd=Urbd(buffer=None,offset=0)
ee=Urbe(buffer=None,offset=0)
ff=Urbf(buffer=None,offset=0)
gg=Urbg(buffer=None,offset=0)
hh=Urbh(buffer=None,offset=0)
ii=Urbi(buffer=None,offset=0)
nn=New_Urb(buffer=None,offset=0)
rr=Urbr(buffer=None,offset=0)
ss=Urbs(buffer=None,offset=0)
ssu=Urbsu(buffer=None,offset=0)
tt=Urbt(buffer=None,offset=0)
uu=Urbu(buffer=None,offset=0)
ii_isns=Urbi_isns(buffer=None,offset=0)
[docs]def setURBebcdic(TrueFalse):
"""Set all URB blocks to EBCDIC or not.
Implicitely the byte encoding will be set to CP037 or Latin1
:param TrueFalse: True (set to EBDIC) or False
"""
cc.setEbcdic(TrueFalse)
dd.setEbcdic(TrueFalse)
ee.setEbcdic(TrueFalse)
ff.setEbcdic(TrueFalse)
gg.setEbcdic(TrueFalse)
hh.setEbcdic(TrueFalse)
ii.setEbcdic(TrueFalse)
nn.setEbcdic(TrueFalse)
rr.setEbcdic(TrueFalse)
ss.setEbcdic(TrueFalse)
ssu.setEbcdic(TrueFalse)
tt.setEbcdic(TrueFalse)
uu.setEbcdic(TrueFalse)
ii_isns.setEbcdic(TrueFalse)
[docs]def setURBnwbo():
"""set all URB blocks to NETWORKBO byte order"""
cc.byteOrder=dd.byteOrder=ee.byteOrder=hh.byteOrder=ii.byteOrder=datamap.NETWORKBO
ff.byteOrder=gg.byteOrder=datamap.NETWORKBO
rr.byteOrder=ss.byteOrder=ssu.byteOrder=tt.byteOrder=uu.byteOrder=datamap.NETWORKBO
ii_isns=nn.byteOrder=datamap.NETWORKBO
[docs]def makeURBH(buffer, msgNo=0, senderName='Admin'):
"""write URB header at beginning of buffer
:param msgNo: message number (optional)
:param senderName: 8 byte name identifying the sender
"""
hh.buffer=buffer
hh.offset=0
hh.urbheye=URBHEYE
hh.urbhlen=URBHL
hh.urbhvers=URBHVER1
hh.urbhbord=URBHBORD
hh.urbhlent=URBHL # current / total msg length
hh.urbhmsnr=msgNo # msg seq number per sender
hh.urbhtime=0
hh.urbhrpid=0
hh.urbhrpni=0
hh.urbhname=senderName
def setTotalLength(totalLength):
if totalLength > len(hh.buffer):
raise ReptorError( 'new total length %d exceeds buffer size %d' %
(totalLength,len(hh.buffer)) )
hh.urbhlent=totalLength
[docs]def makeURBS(token='TEST'):
""" create an URBS which can be received on an output queue
:param token: token for URBS
:return: current message size
"""
if URBSL+hh.urbhlent > len(hh.buffer):
raise ReptorError( 'Buffer full: %d + %d > %d' %\
(hh.urbhlent,URBSL,len(hh.buffer)))
ss.buffer=hh.buffer
ss.offset=hh.urbhlent
ss.urbseye=URBSEYE
ss.urbslen=URBSL
ss.urbslenh=URBIL
ss.urbslend=0
ss.urbsrtok=token
ss.urbsrt=''
ss.urbsst='TEST'
setTotalLength(ss.offset+URBSL)
return ss.offset+URBSL # return current message size
[docs]def requestInst(dbid=0,fnr=0,instname='',token='INSTREQU',
rspDest='',isnl=[],value='',arc=0,acode='',wcode=''):
""" create URBI with initial state request element for an initial
state definition
:param instname: initial state name and
:param dbid: database id
:param fnr: file number
optional are:
:param rspDest: response destination
:param isnl: selected ISN list
:param value: selection value
:param arc: architecture
:param acode: alfa encoding
:param wcode: wide encoding
:return: current message size
"""
if URBIL+hh.urbhlent > len(hh.buffer):
raise ReptorError( 'Buffer full: %d + %d > %d' %\
(hh.urbhlent,URBIL,len(hh.buffer)))
ii.buffer=hh.buffer
ii.offset=hh.urbhlent
ii.urbieye=URBIEYE
ii.urbilen=URBIL
ii.urbilenh=URBIL
ii.urbilend=0
ii.urbirtok=token
ii.urbirnam=rspDest # destination name for response
ii.urbirt=URBIRTIS # Initial-state request type
ii.urbidbid=dbid
ii.urbifnr=fnr
ii.urbiinam=instname
ii.urbisnam=''
ii.urbidnam=''
i0=ii.offset+URBIL
if len(value) > 0: # value for selection criterion
if len(isnl)>0:
raise ReptorError(
'ISN(s) and selection value cannot be specified both')
else:
hh.buffer[i0:i0+len(value)]=value
i1=len(value)
ii.urbilend=i1
ii.urbilen=i1+URBIL
i1+=i0
setTotalLength(i1)
ii.urbiarc=arc
ii.urbiacod=ecscodec.getecs(acode)
ii.urbiwcod=ecscodec.getecs(wcode)
return i1
elif len(isnl)==0: # no ISN list -> complete file
setTotalLength(i0)
return i0 # return current message size
else: # ISN list
ii_isns.buffer=hh.buffer
ii_isns.offset=ii.offset+URBIL
for i in isnl:
if type(i) is list:
ii_isns.urbiirange=URBIIRANGE
ii_isns.urbiisn1=i[0]
ii_isns.urbiisn2=i[1]
ii_isns.offset+=URBIIRANGELEN
else:
ii_isns.urbiisn=i
ii_isns.offset+=URBIISNLEN
i1=ii_isns.offset
ii.urbilend=i1-i0
ii.urbilen=i1-i0+URBIL
setTotalLength(i1)
return i1 # return current message size
[docs]def requestPriorTrans(destination='', rspDest='', subscription='',
transSeqno=0, token='PRIORRQ'):
"""create URBI Prior Transaction request element for
subscription, transaction sequence number within subscription
and destination
if rspDest (response destination) it will receive
a status response URBS as well
returns current message size
"""
if URBIL+hh.urbhlent > len(hh.buffer):
raise ReptorError( 'Buffer full: %d + %d > %d' %\
(hh.urbhlent,URBIL,len(hh.buffer)))
if transSeqno<=0:
raise ReptorError( 'transSeqno %d must be > 0' % transSeqno)
ii.buffer=hh.buffer
ii.offset=hh.urbhlent
ii.urbieye=URBIEYE
ii.urbilen=URBIL
ii.urbilenh=URBIL
ii.urbilend=0
ii.urbirtok=token
ii.urbirnam=rspDest # destination name for response
ii.urbirt=URBIRTTA # request type: Prior transaction seqno
ii.urbidbid=0
ii.urbifnr=0
ii.urbiinam=''
ii.urbisnam=subscription
ii.urbidnam=destination
ii.urbitsnr=transSeqno
setTotalLength(ii.offset+URBIL)
return ii.offset+URBIL # return current message size
[docs]def requestStatus(destination='', rspDest='', subscription='',
token='STATUSRQ'):
"""create URBI status request element for
destination and/or subscription
if rspDest (response destination) it will receive
a status response URBS as well
returns current message size
"""
if URBIL+hh.urbhlent > len(hh.buffer):
raise ReptorError( 'Buffer full: %d + %d > %d' %\
(hh.urbhlent,URBIL,len(hh.buffer)))
ii.buffer=hh.buffer
ii.offset=hh.urbhlent
ii.urbieye=URBIEYE
ii.urbilen=URBIL
ii.urbilenh=URBIL
ii.urbilend=0
ii.urbirtok=token
ii.urbirnam=rspDest # destination name for response
ii.urbirt=URBIRTST # status request type
ii.urbidbid=0
ii.urbifnr=0
ii.urbiinam=''
ii.urbisnam=subscription
ii.urbidnam=destination
setTotalLength(ii.offset+URBIL)
return ii.offset+URBIL # return current message size
[docs]def requestCloseDest(destination='', rspDest='', token='CLSDrqst'):
"""create URBI 'close destination' request element for destination
if rspDest (response destination) it will receive
a status response URBS as well
returns current message size
"""
if URBIL+hh.urbhlent > len(hh.buffer):
raise ReptorError( 'Buffer full: %d + %d > %d' %\
(hh.urbhlent,URBIL,len(hh.buffer)))
ii.buffer=hh.buffer
ii.offset=hh.urbhlent
ii.urbieye=URBIEYE
ii.urbilen=URBIL
ii.urbilenh=URBIL
ii.urbilend=0
ii.urbirtok=token
ii.urbirnam=rspDest # destination name for response
ii.urbirt=URBIRTCD # Close destination request type
ii.urbidbid=0
ii.urbifnr=0
ii.urbiinam=''
ii.urbisnam=''
ii.urbidnam=destination
setTotalLength(ii.offset+URBIL)
return ii.offset+URBIL # return current message size
[docs]def requestOpenDest(destination='', rspDest='', token='OPNDrqst'):
"""create URBI 'open destination' request element for destination
if rspDest (response destination) it will receive
a status response URBS as well
returns current message size
"""
if URBIL+hh.urbhlent > len(hh.buffer):
raise ReptorError( 'Buffer full: %d + %d > %d' %\
(hh.urbhlent,URBIL,len(hh.buffer)))
ii.buffer=hh.buffer
ii.offset=hh.urbhlent
ii.urbieye=URBIEYE
ii.urbilen=URBIL
ii.urbilenh=URBIL
ii.urbilend=0
ii.urbirtok=token
ii.urbirnam=rspDest # destination name for response
ii.urbirt=URBIRTOD # 'Open destination' request type
ii.urbidbid=0
ii.urbifnr=0
ii.urbiinam=''
ii.urbisnam=''
ii.urbidnam=destination
setTotalLength(ii.offset+URBIL)
return ii.offset+URBIL # return current message size
LOGURBH=1
LOGURBT=2
LOGURBR=4
LOGURBD=8
LOGURBDD=16 # LOG DATA of URBD
LOGURBE=32 # LOG end of transaction
LOGURBDM=64 # LOG datamap of data of URBD
LOGURBC=128
LOGURBU=256
LOGURBS=512
LOGURBI=1024
LOGURBF=2**11 # log URBF and URBG
LOGallURB=2**12-1
[docs]class Replicator(object):
""" Replicator class can process replication data
A provider or consumer of replication stream
can set handlers via setHandler() which will be called
to process the different URB* messages
"""
handUrbc=None
handUrbd=None
handUrbe=None
handUrbf=None
handUrbi=None
handUrbh=None
handUrbr=None
handUrbs=None
handUrbt=None
handUrbu=None
typ = 0 # input type # urbh type
perrors = 0 # number of errors detected
pcount = 0 # number of buffers or records processed
logging = 0
ecodec = 'cp037'
[docs] def process(self, buffer, length, status=0, substat=None):
""" Process a message received from Reptor
:param status: uow status
:param substat: may reference the subscription status class instance
for processing subscription data
:param subconf: may reference the subscription and
subscription-file configuration for processing subscription data
"""
self.pcount += 1 # count number of process() calls
if length < 32: # minimum URB header is 32
self.perrors += 1 # count processing errors
log.error('Replication Record %d: too short' % self.pcount)
dump(buffer[:length],log=log.error,ecodec=self.ecodec)
return
# the first record or buffer decides for the rest if it is
# - messages from broker or ADARIS: always starts with URBH
# - ASCII or EBCDIC format of the URBs
# - other type is from ADARPE: URBs in EBCDIC and Network byte order
# if self.pcount == 1:
if 1: # ADARIS binary output may have records starting with URBH and other URB types
# intermixed
# datamap.dataIsEbcdic=0 (default)
# datamap.setNativeByteOrder() (default)
if buffer[0:3] == b'\xE4\xD9\xC2': # URBx in EBCDIC?
# datamap.dataIsEbcdic = 1
setURBebcdic(True)
if buffer[3:4] == b'\xC8':
self.typ |= typURBH
if buffer[10:12] == b'\x00\x01':
# datamap.setNetworkByteOrder()
setURBnwbo()
else: # ADARPE type (no URBH)
# datamap.setNetworkByteOrder()
self.typ &= ~typURBH # reset possible URBH type
setURBnwbo()
elif buffer[0:3] == b'URB':
if buffer[3:4] == b'H':
self.typ |= typURBH
# setURBebcdic(False) # default
if buffer[10:12] == b'\x00\x01':
# datamap.setNetworkByteOrder()
setURBnwbo()
else:
self.typ &= ~typURBH # reset possible URBH type
else:
self.perrors += 1 # count processing errors
log.error('Replication Record % d: no URB* prefix detected' % self.pcount)
dump(buffer,header='Buffer received',log=log.error,ecodec=self.ecodec)
raise ReptorError('No URB* prefix detected but "%s"'% (buffer[:3],))
if __debug__:
if self.logging & LOGallURB: # any logging
log.debug('URB in EBCDIC = %d, URBH messages = %d' % (datamap.dataIsEbcdic, self.typ & typURBH))
if self.typ & typURBH:
hh.buffer=buffer
hh.offset=0
if hh.urbheye != URBHEYE:
self.perrors += 1 # count processing errors
log.error('Replication Record % d: no URBH prefix detected' % self.pcount)
dump(buffer[:length],log=log.error,ecodec=self.ecodec)
return
if hh.urbhvers != URBHVER1:
log.error('Record %d: incompatible URBH version %s received / expected %s:' %\
(self.pcount, hh.urbhvers, URBHVER1))
dump(buffer[:length],log=log.error,ecodec=self.ecodec)
return
total_length=hh.urbhlent
if __debug__:
if self.logging & LOGURBH: log.debug('\n\nURBH %s msg %d total-len %d rpid %d/%d %s\n' %
(stck.sstckd(hh.urbhtime), hh.urbhmsnr, hh.urbhlent, hh.urbhrpid, hh.urbhrpni, hh.urbhname))
if self.handUrbh:
self.handUrbh(hh, substat)
offset = URBHL
rest_length = total_length - URBHL
else:
offset = 0
rest_length = length
while rest_length > 4:
nn.buffer=buffer
nn.offset=offset
if nn.eye == URBDEYE:
dd.buffer=buffer
dd.offset=offset
if __debug__:
if self.logging & LOGURBD:
log.debug('URBD(%d) %s' % (dd.urbddsnr, urbd_type[dd.urbdtyp]))
if self.logging & LOGURBDD:
datalen = dd.urbdlend
dump(dd.buffer[offset+URBDL:offset+URBDL+datalen],
header=None, prefix=' ',log=log.debug,ecodec=self.ecodec)
if self.handUrbd:
self.handUrbd(dd, substat)
rest_length -= dd.urbdlen
offset+=dd.urbdlen
elif nn.eye == URBEEYE:
ee.buffer=buffer
ee.offset=offset
if __debug__:
if self.logging & LOGURBE:
log.debug('URBE -- end of transaction %d for subscription %s' % \
(ee.urbetsnr, ee.urbesnam))
rest_length -= URBEL
offset+=URBEL
if self.handUrbe:
self.handUrbe(ee, substat)
elif nn.eye == URBREYE:
rr.buffer=buffer
rr.offset=offset
if __debug__:
if self.logging & LOGURBH:
log.debug('URBR -- %s record fnr %d isn %d' % \
(urbr_type[rr.urbrtyp], rr.urbrfnr, rr.urbrisn))
if rr.urbrrsp:
rspTxt=''
rspTxt=adaerror.rsptext(rr.urbrrsp,rr.urbrsubc,erri=rr.urbrerrc)
log.debug( rspTxt )
if self.handUrbr:
self.handUrbr(rr, substat)
rest_length-=URBRL
offset+=URBRL
elif nn.eye == URBTEYE:
tt.buffer=buffer
tt.offset=offset
if __debug__:
if self.logging & LOGURBT:
if tt.urbtarc > b'\x00':
encstr = 'arc=%d, acode=%s, wcode=%s' %\
(ord(tt.urbtarc), ecscodec.getcodec(tt.urbtacod),
ecscodec.getcodec(tt.urbtwcod))
else:
encstr=''
log.debug('URBT -- transaction %d with %d records for subscription %s\n'\
' guid %s\n'\
' ET %s dbid %d/%d\n'\
' RP %s rpid %d/%d %s' % \
(tt.urbttsnr, tt.urbtrcnt, tt.urbtsnam,
binascii.hexlify(tt.urbtguid),
stck.sstckd(tt.urbtttim), tt.urbtdbid, tt.urbtnuci,
stck.sstckd(tt.urbtptim), tt.urbtrpid, tt.urbtrpni,
encstr))
if tt.urbtrsnd==URBTRSNY:
log.debug(' -- possible double delivery --')
if tt.urbtinst==URBTINSY:
log.debug(' -- initial state --')
if tt.urbtcont==URBTCONY:
log.debug(' -- to be continued with next message --')
if self.handUrbt:
self.handUrbt(tt, substat)
rest_length-=URBTL
offset+=URBTL
elif nn.eye == URBCEYE:
cc.buffer=buffer
cc.offset=offset
if __debug__:
if self.logging & LOGURBC:
log.debug('URBC -- transaction %d continued record %d dseq %d subs %s\n'\
% (cc.urbctsnr, cc.urbcrsnr, cc.urbcdsnr, cc.urbcsnam))
if cc.urbccont==URBTCONY:
log.debug(' -- to be continued with next message --')
if self.handUrbc:
self.handUrbc(cc, substat)
rest_length-=URBCL
offset+=URBCL
elif nn.eye == URBSEYE:
ss.buffer=buffer
ss.offset=offset
if __debug__:
if self.logging & LOGURBS:
subcTxt = ''
if ss.urbsrsp > 0:
subcTxt=' -'+str(ss.urbssubc)
if ss.urbsrsp==REPTOR_RSP:
if 0 < ss.urbssubc < len(texts_reptor_subcodes):
subcTxt += '- '+texts_reptor_subcodes[ss.urbssubc]
else:
if ss.urbsrsp in adaerror.rspdict:
subcTxt += ' - '+adaerror.rspdict[ss.urbsrsp]
log.debug('URBS %s -- %s\n' \
' subs %s dest %s init %s rsp %d%s %s\n'\
' ET %s dbid %d fnr %d\n'\
' RP %s tsnr %d rtok %r' % \
(stck.sstckd(ss.urbstime),
urbs_status.get(ss.urbsst,ss.urbsst),
ss.urbssnam, ss.urbsdnam, ss.urbsinam,
ss.urbsrsp, subcTxt, ss.urbserri,
stck.sstckd(ss.urbsttim), ss.urbsdbid, ss.urbsfnr,
stck.sstckd(ss.urbsptim), ss.urbstsnr, ss.urbsrtok))
datalen = ss.urbslend
if datalen > 0:
if ss.urbsst == URBSSTAU: # online utility
ssu.buffer=buffer
ssu.offset=offset+URBSL
ssu.dprint()
elif xtra:
xtra.urbslog(ss)
else:
dump(ss.buffer[offset+URBSL:offset+URBSL+datalen],
header=' Reptor Status/Response Data',
prefix=' ',log=log.debug,ecodec=self.ecodec)
if self.handUrbs:
self.handUrbs(ss, substat)
rest_length -= ss.urbslen
offset += ss.urbslen
elif nn.eye == URBIEYE:
ii.buffer=buffer
ii.offset=offset
if __debug__:
if self.logging & LOGURBI:
if ii.urbirt != URBIRTST and ii.urbirt != URBIRTIS:
rtypeText = 'Unknown request type ' + ii.urbirt
else:
rtypeText = urbi_rtext[ii.urbirt]
log.debug('URBI %s -- token %s\n' \
' subs %s dest %s rdest %s\n' \
' init %s dbid %d fnr %d\n' % \
(rtypeText, ii.urbirtok,
ii.urbisnam, ii.urbidnam, ii.urbirnam,
ii.urbiinam, ii.urbidbid, ii.urbifnr))
datalen = ii.urbilend
if datalen > 0:
dump(ii.buffer[offset+URBIL:offset+URBIL+datalen],
header=' Initial-state selection', prefix=' ',log=log.debug)
if self.handUrbi:
self.handUrbi(ii, substat)
rest_length-=ii.urbilen
offset+=ii.urbilen
elif nn.eye == URBUEYE:
uu.buffer=buffer
uu.offset=offset
if __debug__:
if self.logging & LOGURBU:
log.debug('URBU -- ADARPE %s extract from %s (local time)\n'\
% (uu.urbuname, uu.urbudist))
if self.handUrbu:
self.handUrbu(uu, substat)
rest_length -= URBUL
offset += URBUL
elif nn.eye == URBFEYE: # global format field table (GFFT)
ff.buffer = buffer
ff.offset = offset
if __debug__:
if self.logging & LOGURBF:
# ff.urbffnam[: ff.urbffnml]
log.debug('URBF -- gfid=%s db=%d, fnr=%d\n' \
' fnam=%s, items=%d\n' \
' created=%s with %s\n%s' %
(ff.urbfgfid, ff.urbfdbid, ff.urbffnr,
ff.urbffnam,ff.urbfcntg,
stck.sstckd(ff.urbftim1)[0:19],
urbfflag_str(ff.urbfflag),
' processed=%s\n' % stck.sstckd(ff.urbftim2)[0:19]
if ff.urbftim2 else ''
))
datalen = ff.urbflend
if datalen > 0:
gg.buffer = buffer
gg.offset = offset+URBFL
for i in range(ff.urbfcntg):
gg.dprint()
gg.offset += URBGL
rest_length -= ff.urbflen
offset += ff.urbflen
if self.handUrbf:
self.handUrbf(ff, substat)
else:
log.error('Unknown Structure %s' % nn.eye)
dump(buffer[offset:offset+rest_length],log=log.error,ecodec=self.ecodec)
break
def setHandler(self, urbType, function):
# print( 'setHandler called', urbType, function)
if urbType=='URBC':
self.handUrbc=function
elif urbType=='URBD':
self.handUrbd=function
elif urbType=='URBE':
self.handUrbe=function
elif urbType=='URBF':
self.handUrbf=function
elif urbType=='URBH':
self.handUrbh=function
elif urbType=='URBR':
self.handUrbr=function
elif urbType=='URBS':
self.handUrbs=function
elif urbType=='URBT':
self.handUrbt=function
elif urbType=='URBI':
self.handUrbi=function
elif urbType=='URBU':
self.handUrbu=function
else:
raise ReptorError( 'unknown structure %s'% (urbType,))
__version__ = 'v.r.l'
if __version__ == 'v.r.l':
_svndate='$Date: 2023-12-01 00:54:33 +0100 (Fri, 01 Dec 2023) $'
_svnrev='$Rev: 1072 $'
__version__ = 'Dev ' + _svnrev.strip('$') + \
' '.join(_svndate.strip('$').split()[0:3])
# Copyright 2004-ThisYear Software AG
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.