/usr/share/gnudatalanguage/astrolib/dbwrt.pro is in gdl-astrolib 2018.02.16+dfsg-1.
This file is owned by root:root, with mode 0o644.
The actual contents of the file can be viewed below.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 | pro dbwrt,entry,index,append,noconvert=noconvert
;+
; NAME:
; DBWRT
; PURPOSE:
; procedure to update or add a new entry to a data base
;
; CALLING SEQUENCE:
; dbwrt, entry, [ index, append, /NoConvert ]
;
; INPUTS:
; entry - entry record to be updated or added if first
; item (entry number=0)
;
; OPTIONAL INPUTS:
; index - optional integer flag, if set to non zero then index
; file is updated. (default=0, do not update index file)
; (Updating the index file is time-consuming, and should
; normally be done after all changes have been made.
; append - optional integer flag, if set to non-zero the record
; is appended as a new entry, regardless of what the
; entry number in the record is. The entry number will
; be reset to the next entry number in the file.
; OUTPUTS:
; data base file is updated.
; If index is non-zero then the index file is updated.
; OPTIONAL INPUT KEYWORD:
; NoConvert - If set then don't convert to host format with an external
; database. Useful when the calling program decides that
; conversion isn't needed (i.e. on a big-endian machine), or
; takes care of the conversion itself.
; OPERATIONAL NOTES:
; !PRIV must be greater than 1 to execute
; HISTORY:
; version 2 D. Lindler Feb. 1988 (new db format)
; converted to IDL Version 2. M. Greason, STX, June 1990.
; William Thompson, GSFC/CDS (ARC), 28 May 1994
; Added support for external (IEEE) representation.
; Faster handling of byte swapping W. L. August 2010
; Updates for indexing on the fly, D.Lindler, June, 2016
;-
;-------------------------------------------------------------------
COMMON db_com,qdb,qitems,qdbrec
if N_params() LT 2 then index=0
if N_params() LT 3 then append=0
; Byte swapping is needed if database is in external format, and user is on
; a little endian machine, and /noconvert is not st
bswap = (qdb[119] eq 1) && ~keyword_set(noconvert) && ~is_ieee_big()
; get some info on the data base
update = db_info( 'UPDATE' )
if update EQ 0 then message,'Database opened for read only'
len = db_info( 'LENGTH', 0 ) ;record length
qnentry = db_info( 'ENTRIES', 0 )
; determine if entry is correct size
s = size(entry)
if s[0] NE 1 then message,'Entry must be a 1-dimensional array'
if s[1] NE len then $
message,'Entry not the proper length of '+strtrim(len,2)+' bytes'
if s[2] NE 1 then $
message,'Entry vector (first parameter) must be a byte array'
; get entry number
enum = append ? 0 : dbxval(entry,3,1,0,4)
if ( enum GT qnentry ) || ( enum LT 0 ) then $
message,'Invalid entry number of '+strtrim(enum,2)+' (first value in entry)'
if enum EQ 0 then begin ;add new entry
qnentry = qnentry+1
qdb[84] = byte(qnentry,0,4)
enum = qnentry
dbxput,long(enum),entry,3,0,4
newentry = 1b
endif else newentry =0b
if bswap then begin
tmp = entry
db_ent2ext, tmp
qdbrec[enum]=tmp
endif else qdbrec[enum] = entry
; update index file if necessary
if index EQ 0 then return
nitems = db_info( 'ITEMS', 0 ) ;Total number of items
indextype = db_item_info( 'INDEX', indgen(nitems)) ;Which ones are indexed?
indexed = where(indextype,nindex)
if nindex LE 0 then return ;If no indexed items, then we are done
indextype = indextype[indexed] ;Now contains only indexed items
unit = db_info( 'UNIT_DBX', 0 )
reclong = assoc(unit,lonarr(2),0)
h = reclong[0]
maxentries = h[1]
if bswap then swap_endian_inplace, maxentries
if newentry then $
if (maxentries LT qnentry) then begin ;Enough room for new indexed items?
print,'DBWRT -- maxentries too small'
print,'Rerun DBCREATE with maxentries in .dbd file at least ',qnentry
return
endif
reclong = assoc(unit,lonarr(7,nindex),8)
header = reclong[0]
if bswap then swap_endian_inplace,header
hitem = header[0,*] ;indexed item number
hblock = header[3,*]
sblock = header[4,*] & sblock = sblock[*]
iblock = header[5,*] & iblock = iblock[*]
ublock = header[6,*] & ublock = ublock[*]
db_item, indexed, itnum, ivalnum, idltype, startbyte, numvals, nbytes
pos = where(hitem EQ itnum )
for i = 0, nindex-1 do begin
v = dbxval( entry, idltype[i], numvals[i], startbyte[i], nbytes[i] )
sbyte = nbytes[i] * (enum-1)
isort = (indextype[i] EQ 3) || (indextype[i] EQ 4)
datarec = dbindex_blk(unit, sblock[pos[i]], 512, sbyte, idltype[i])
reclong = assoc(unit,lonarr(1),(iblock[pos[i]]*512L))
if idltype[i] eq 7 then v = byte(v) ; convert string to a byte array
if n_elements(v) eq 1 then v = reform(v,1,/overwrite) ; make scale into an array
case indextype[i] of
1: datarec[0] = bswap ? swap_endian(v) : v
2: begin
datarec[0] = bswap ? swap_endian(v) : v
if (qnentry mod 512) EQ 0 then begin ;Update
nb = qnentry/512
hbyte = nbytes[i] * nb
datarec = dbindex_blk(unit,hblock[pos[i]],512,hbyte,idltype[i])
datarec[0] = bswap ? swap_endian(v) : v
endif
end
3: begin ;SORT
datarec = dbindex_blk(unit,sblock[pos[i]],512,0,idltype[i])
values = datarec[0:(qnentry-1)] ;Read in old values
if bswap then swap_endian_inplace, values
reclong = dbindex_blk(unit,iblock[pos[i]],512,0,3)
sub = reclong[0:(qnentry-1)] ;Read in old indices
if bswap then swap_endian_inplace, sub
if enum lt qnentry then begin ;Change an old value?
sort_index = where(sub EQ enum) ;Which value to change
sort_index = sort_index[0]
if values[sort_index] EQ v $ ;Value remains the same so
then isort =0 $ ;don't bother sorting again
else values[sort_index] = v ;Update with new value
endif else values = [values,v] ;Append a new value
end
4: begin ;SORT/INDEX
values = datarec[qnentry-1,ublock*512] ;Update index record
if bswap then swap_endian_inplace, values
if enum lt qnentry then begin
if values[enum-1] EQ v then isort = 0 else values[enum-1] = v
endif else values = [values,v]
datarec = dbindex_blk(unit,ublock[pos[i]],512,sbyte,idltype[i])
datarec[0] = bswap ? swap_endian(v) : v
end
else:
endcase
if isort then begin ;resort values?
sub = bsort(values)
values = values[sub]
nb = (qnentry + 511)/512
ind = indgen(nb)*512L
sval = values[ind]
;
datarec = dbindex_blk(unit, hblock[pos[i]], 512, 0, idltype[i])
datarec[0] = bswap ? swap_endian(sval) : sval
;
datarec = dbindex_blk(unit, sblock[pos[i]], 512, 0, idltype[i])
datarec[0] = bswap ?swap_endian(values) : values
;
reclong = dbindex_blk(unit, iblock[pos[i]], 512, 0, 3)
reclong[0] = bswap ?swap_endian(sub+1) : sub+1
endif
endfor
return
end
|