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 198 199 200 201
|
/*
BINSTD.C
Define various standard binary data formats.
$Id: binstd.c,v 1.1 1993/08/27 18:32:09 munro Exp $
*/
/* Copyright (c) 1994. The Regents of the University of California.
All rights reserved. */
#include "binio.h"
#include "defmem.h"
/* ------------------------------------------------------------------------ */
/* FLOATING POINT FORMATS */
/* ------------------------------------------------------------------------ */
extern FPLayout fp4ieee, fp8ieee, fp12ieee,
fp8cray, fp4vax, fp8hvax, fp8gvax;
#define REF_COUNTER 0
/* S& E& E# M& M# M? E-bias */
FPLayout fp4ieee= {REF_COUNTER, 0, 1, 8, 9, 23, 0, 0x7fL};
FPLayout fp8ieee= {REF_COUNTER, 0, 1, 11, 12, 52, 0, 0x3ffL};
FPLayout fp12ieee= {REF_COUNTER, 0, 1, 15, 32, 64, 1, 0x3ffeL};
FPLayout fp8cray= {REF_COUNTER, 0, 1, 15, 16, 48, 1, 0x4000L};
FPLayout fp4vax= {REF_COUNTER, 0, 1, 8, 9, 23, 0, 0x81L};
FPLayout fp8hvax= {REF_COUNTER, 0, 1, 8, 9, 55, 0, 0x81L};
FPLayout fp8gvax= {REF_COUNTER, 0, 1, 11, 12, 52, 0, 0x401L};
/* S& bit address of sign
E& bit address of exponent
E# number of bits in exponent
M& bit address of mantissa
M# number of bits in mantissa
M? 0 iff high order mantissa bit (always 1) is implicit
E-bias exponent bias
*/
static long knownSizes[]= {4, 8, 12, 16, 0};
static FPLayout *known4[]= {&fp4ieee, &fp4vax, 0};
static FPLayout *known8[]= {&fp8ieee, &fp8cray, &fp8hvax, &fp8gvax, 0};
static FPLayout *known12[]= {&fp12ieee, 0};
static FPLayout *known16[]= {0};
static FPLayout *knownMisc[]= {0};
static FPLayout **knownLayouts[]= {
known4, known8, known12, known16, knownMisc};
/* ------------------------------------------------------------------------ */
/* BIG-ENDIAN MACHINES */
/* ------------------------------------------------------------------------ */
extern DataLayout bigendLayout[6], sun3Layout[6], pdbLayout[6],
crayLayout[6], cchybridLayout[6], mac4Layout[7], mac2Layout[7];
/* Each data type is represented by {alignment, size, order, fpLayout},
and each machine has an array of 6 types in the order:
char, short, int, long, float, double
Some machines include an alternate form of double as a 7th type.
*/
/* The primitive data type formats are the same for the following
machines:
Sun SPARC, HP 700 series, IBM RS6000, SGI, and MIPS workstations
*/
DataLayout bigendLayout[6]= {
{1, 1, 1, 0}, {2, 2, 1, 0}, {4, 4, 1, 0}, {4, 4, 1, 0},
{4, 4, 1, &fp4ieee}, {8, 8, 1, &fp8ieee}
};
/* Sun-2 and Sun-3 (M68000-based) have less restrictive alignments */
DataLayout sun3Layout[6]= {
{1, 1, 1, 0}, {2, 2, 1, 0}, {2, 4, 1, 0}, {2, 4, 1, 0},
{2, 4, 1, &fp4ieee}, {2, 8, 1, &fp8ieee}
};
/* Default for old PDBLib corresponds to no known machine (?!) */
DataLayout pdbLayout[6]= {
{1, 1, 1, 0}, {4, 2, 1, 0}, {4, 4, 1, 0}, {4, 4, 1, 0},
{4, 4, 1, &fp4ieee}, {4, 8, 1, &fp8ieee}
};
/* Unicos Cray 1, XMP, YMP machines */
DataLayout crayLayout[6]= {
{1, 1, 1, 0}, {8, 8, 1, 0}, {8, 8, 1, 0}, {8, 8, 1, 0},
{8, 8, 1, &fp8cray}, {8, 8, 1, &fp8cray}
};
/* Defunct (?) hybrid C compiler on LTSS Crays */
DataLayout cchybridLayout[6]= {
{8, 1, 1, 0}, {8, 8, 1, 0}, {8, 8, 1, 0}, {8, 8, 1, 0},
{8, 8, 1, &fp8cray}, {8, 8, 1, &fp8cray}
};
/* MacIntosh has both 12 and 8 byte double formats, and
compilers disagree about the size of an int */
DataLayout mac4Layout[7]= {
{1, 1, 1, 0}, {2, 2, 1, 0}, {2, 4, 1, 0}, {2, 4, 1, 0},
{2, 4, 1, &fp4ieee}, {2, 12, 1, &fp12ieee},
{2, 8, 1, &fp8ieee}
};
/* NOTE NOTE NOTE -- the fact that the 12 byte double is listed BEFORE
the 8 byte double is significant in binpdb.c */
DataLayout mac2Layout[7]= {
{1, 1, 1, 0}, {2, 2, 1, 0}, {2, 2, 1, 0}, {2, 4, 1, 0},
{2, 4, 1, &fp4ieee}, {2, 12, 1, &fp12ieee},
{2, 8, 1, &fp8ieee}
};
/* ------------------------------------------------------------------------ */
/* LITTLE-ENDIAN MACHINES */
/* ------------------------------------------------------------------------ */
extern DataLayout littleLayout[6], ibmpcLayout[6], xenixLayout[6],
vaxLayout[7];
/* DEC workstations are little-endian version of bigendLayout
IBM PC differs only in having a less restrictive alignment,
and the XENIX OS on PCs differs in int size from that */
DataLayout littleLayout[6]= {
{1, 1, -1, 0}, {2, 2, -1, 0}, {4, 4, -1, 0}, {4, 4, -1, 0},
{4, 4, -1, &fp4ieee}, {8, 8, -1, &fp8ieee}
};
DataLayout ibmpcLayout[6]= {
{1, 1, -1, 0}, {2, 2, -1, 0}, {2, 2, -1, 0}, {2, 4, -1, 0},
{2, 4, -1, &fp4ieee}, {2, 8, -1, &fp8ieee}
};
DataLayout xenixLayout[6]= {
{1, 1, -1, 0}, {2, 2, -1, 0}, {2, 4, -1, 0}, {2, 4, -1, 0},
{2, 4, -1, &fp4ieee}, {2, 8, -1, &fp8ieee}
};
/* VAX has G-format and H-format doubles, as well as
odd byte ordering for all of its floating point formats. */
/* WARNING --
Did I read the lack-of-alignment in the VAX C manual correctly?
PDBLib uses alignment of 4 for all but char... */
DataLayout vaxLayout[7]= {
{1, 1, -1, 0}, {1, 2, -1, 0}, {1, 4, -1, 0}, {1, 4, -1, 0},
{1, 4, -2, &fp4vax}, {1, 8, -2, &fp8hvax},
{1, 8, -2, &fp8gvax}
};
/* ------------------------------------------------------------------------ */
/* END OF DATA LAYOUTS */
/* ------------------------------------------------------------------------ */
FPLayout *MakeFPLayout(FPLayout *model, long size)
{
int i;
FPLayout **list, *layout;
if (!model) return 0;
/* if this floating point layout is for this machine,
just return reference */
if (size==sizeof(float) &&
SameFPLayout(fltLayout, model)) return Ref(fltLayout);
if (size==sizeof(double) &&
SameFPLayout(dblLayout, model)) return Ref(dblLayout);
/* if this floating point layout is known, just return reference */
for (i=0 ; knownSizes[i] ; i++) if (knownSizes[i]==size) break;
list= knownLayouts[i];
while (*list) {
if (SameFPLayout(*list, model)) return Ref(*list);
list++;
}
/* otherwise, make a fresh copy */
layout= Ymalloc(sizeof(FPLayout));
layout->references= 0;
layout->sgnAddr= model->sgnAddr;
layout->expAddr= model->expAddr;
layout->expSize= model->expSize;
layout->manAddr= model->manAddr;
layout->manSize= model->manSize;
layout->manNorm= model->manNorm;
layout->expBias= model->expBias;
return layout;
}
int SameFPLayout(FPLayout *l, FPLayout *m)
{
return (l->sgnAddr==m->sgnAddr && l->expAddr==m->expAddr &&
l->expSize==m->expSize && l->manAddr==m->manAddr &&
l->manSize==m->manSize && l->manNorm==m->manNorm &&
l->expBias==m->expBias);
}
void FreeFPLayout(FPLayout *layout)
{
if (layout && !layout->references--) Yfree(layout);
}
|