4 #include <ctype.h> /* to declare isprint() */
6 #define str2num(str, typeNum) *((typeNum *)(str))
8 static int _gdcm_read_RLE_fragment (char ** image_buffer,
10 long uncompressedSegmentSize,
12 // static because nothing but gdcm_read_RLE_file may call it
17 // ----------------------------------------------------------------------------
20 * \brief Reads a 'Run Length Encoded' Dicom encapsulated file
21 * @param image_buffer destination Address (in caller's memory space)
23 * pixel data should be copied
24 * @return int acts as a Boolean
27 // This is a debug version.
28 // Forget the printf as they will be removed
29 // as soon as the last Heuristics are checked
32 gdcmFile::gdcm_read_RLE_file (void * image_buffer) {
33 long fragmentBegining; // for ftell, fseek
34 char * im = (char *)image_buffer;
35 if (DEBUG)std::cout << "RLE image" << std::endl;
37 long RleSegmentLength[15],fragmentLength,uncompressedSegmentSize;;
39 guint32 nbRleSegments;
40 guint32 RleSegmentOffsetTable[15];
41 guint16 ItemTagGr,ItemTagEl;
42 uncompressedSegmentSize=GetXSize()*GetYSize();
43 if (DEBUG)printf("uncompressedSegmentSize %d\n",uncompressedSegmentSize);
45 // Basic Offset Table with Item Value
47 fread(&ItemTagGr,2,1,fp); // Reading (fffe):Basic Offset Table Item Tag Gr
48 fread(&ItemTagEl,2,1,fp); // Reading (e000):Basic Offset Table Item Tag El
50 ItemTagGr=SwapShort(ItemTagGr);
51 ItemTagEl=SwapShort(ItemTagEl);
53 if (DEBUG)printf ("at %x : ItemTag (should be fffe,e000): %04x,%04x\n",
54 ftellRes,ItemTagGr,ItemTagEl );
59 ln=SwapLong(ln); // Basic Offset Table Item Lentgh
60 if (DEBUG)printf("at %x : Basic Offset Table Item Lentgh (??) %d x(%08x)\n",
63 // What is it used for ??
64 char * BasicOffsetTableItemValue= (char *)malloc(ln+1);
65 fread(BasicOffsetTableItemValue,ln,1,fp);
67 for (int i=0;i<ln;i+=4){
68 a=str2num(&BasicOffsetTableItemValue[i],guint32);
69 if (DEBUG)printf(" x(%08x) %d\n",a,a);
74 fread(&ItemTagGr,2,1,fp); // Reading (fffe) : Item Tag Gr
75 fread(&ItemTagEl,2,1,fp); // Reading (e000) : Item Tag El
77 ItemTagGr=SwapShort(ItemTagGr);
78 ItemTagEl=SwapShort(ItemTagEl);
80 if (DEBUG)printf ("at %x : ItemTag (should be fffe,e000 or e0dd): %04x,%04x\n",
81 ftellRes,ItemTagGr,ItemTagEl );
83 // while 'Sequence Delimiter Item' (fffe,e0dd) not found
84 while ( ( ItemTagGr == 0xfffe) && (ItemTagEl != 0xe0dd) ) {
85 // Parse fragments of the current Fragment (Frame)
87 fread(&fragmentLength,4,1,fp);
89 fragmentLength=SwapLong(fragmentLength); // length
90 if (DEBUG)printf(" at %x : fragment length %d x(%08x)\n",
91 ftellRes, fragmentLength,fragmentLength);
93 //------------------ scanning (not reading) fragment pixels
95 fread(&nbRleSegments,4,1,fp); // Reading : Number of RLE Segments
97 nbRleSegments=SwapLong(nbRleSegments);
98 if (DEBUG)printf(" Nb of RLE Segments : %d\n",nbRleSegments);
100 for(int k=1; k<=15; k++) { // Reading RLE Segments Offset Table
102 fread(&RleSegmentOffsetTable[k],4,1,fp);
104 RleSegmentOffsetTable[k]=SwapLong(RleSegmentOffsetTable[k]);
105 if (DEBUG)printf(" at : %x Offset Segment %d : %d (%x)\n",
106 ftellRes,k,RleSegmentOffsetTable[k],RleSegmentOffsetTable[k]);
109 if (nbRleSegments>1) {
110 for(int k=1; k<=nbRleSegments-1; k++) { // reading RLE Segments
111 RleSegmentLength[k]=RleSegmentOffsetTable[k+1]-RleSegmentOffsetTable[k];
113 if (DEBUG)printf (" (in) Segment %d : Length = %d x(%x) Start at %x\n",
114 k,RleSegmentLength[k],RleSegmentLength[k], ftellRes);
115 fragmentBegining=ftell(fp);
116 _gdcm_read_RLE_fragment (&im, RleSegmentLength[k],uncompressedSegmentSize,fp);
117 fseek(fp,fragmentBegining,SEEK_SET);
118 fseek(fp,RleSegmentLength[k],SEEK_CUR);
121 RleSegmentLength[nbRleSegments] = fragmentLength - RleSegmentOffsetTable[nbRleSegments];
123 if (DEBUG)printf (" (out)Segment %d : Length = %d x(%x) Start at %x\n",
125 RleSegmentLength[nbRleSegments],RleSegmentLength[nbRleSegments],
127 fragmentBegining=ftell(fp);
128 _gdcm_read_RLE_fragment (&im, RleSegmentLength[nbRleSegments],uncompressedSegmentSize, fp);
129 fseek(fp,fragmentBegining,SEEK_SET);
130 fseek(fp,RleSegmentLength[nbRleSegments],SEEK_CUR);
132 // end of scanning fragment pixels
135 fread(&ItemTagGr,2,1,fp); // Reading (fffe) : Item Tag Gr
136 fread(&ItemTagEl,2,1,fp); // Reading (e000) : Item Tag El
138 ItemTagGr=SwapShort(ItemTagGr);
139 ItemTagEl=SwapShort(ItemTagEl);
141 if (DEBUG)printf ("at %x : ItemTag (should be fffe,e000 or e0dd): %04x,%04x\n",
142 ftellRes,ItemTagGr,ItemTagEl );
148 /* -------------------------------------------------------------------- */
150 // RLE LossLess Fragment
152 /* -------------------------------------------------------------------- */
154 // static because nothing but gdcm_read_RLE_file can call it
158 _gdcm_read_RLE_fragment (char ** areaToRead,
160 long uncompressedSegmentSize,
164 long numberOfOutputBytes=0;
168 while(numberOfOutputBytes<uncompressedSegmentSize) {
171 fread(&n,sizeof(char),1,fp);
173 if (count >= 0 && count <= 127) {
174 fread(*areaToRead,(count+1)*sizeof(char),1,fp);
175 *areaToRead+=count+1;
176 numberOfOutputBytes+=count+1;
178 if (count <= -1 && count >= -127) {
179 fread(&car,sizeof(char),1,fp);
180 for(int i=0; i<-count+1; i++) {
181 (*areaToRead)[i]=car;
183 *areaToRead+=(-count+1);
184 numberOfOutputBytes+=(-count+1);
187 // if count = 128 output nothing (See : PS 3.5-2003 Page 86)