NCEPLIBS-bufr  11.6.0
 All Data Structures Files Functions Variables Pages
crbmg.c
Go to the documentation of this file.
1 
5 #include "bufrlib.h"
6 #include "cobfl.h"
7 
48 void crbmg( char *bmg, f77int *mxmb, f77int *nmb, f77int *iret )
49 {
50  f77int i1 = 1, i2 = 2, i3 = 3, i4 = 4, i24 = 24;
51  f77int wkint[2];
52  f77int iben, isbyt, iwid;
53 
54  char errstr[129];
55 
56  unsigned short i, nsecs;
57  unsigned int lsec;
58 /*
59 ** Make sure that a file is open for reading.
60 */
61  if ( pbf[0] == NULL ) {
62  sprintf( errstr, "BUFRLIB: CRBMG - NO FILE IS OPEN FOR READING" );
63  bort( errstr, ( f77int ) strlen( errstr ) );
64  }
65 /*
66 ** Initialize the first 4 characters of the output array to blanks.
67 */
68  if ( *mxmb < 4 ) {
69  *iret = 1;
70  return;
71  }
72  strncpy( bmg, " ", 4);
73 /*
74 ** Look for the start of the next BUFR message.
75 */
76  while ( ichkstr( "BUFR", bmg, &i4, 4, 4 ) != 0 ) {
77  memmove( bmg, &bmg[1], 3 );
78  if ( ( *iret = rbytes( bmg, mxmb, 3, 1 ) ) != 0 ) return;
79  }
80 /*
81 ** Read the next 4 bytes and determine the BUFR edition number that was used
82 ** to encode the message.
83 */
84  if ( ( *iret = rbytes( bmg, mxmb, 4, 4 ) ) != 0 ) return;
85  memcpy( wkint, bmg, 8 );
86  iben = iupbs01( wkint, "BEN", 3 );
87 
88  if ( iben >= 2 ) {
89 /*
90 ** Get the length of the BUFR message.
91 */
92  *nmb = iupbs01( wkint, "LENM", 4 );
93 /*
94 ** Read the remainder of the BUFR message.
95 */
96  if ( ( *iret = rbytes( bmg, mxmb, 8, *nmb-8 ) ) != 0 ) return;
97  }
98  else {
99 /*
100 ** Read the remainder of the BUFR message and then convert it to BUFR
101 ** edition 2. The message length isn't encoded in Section 0, so we need
102 ** to compute it by unpacking and summing the lengths of the individual
103 ** sections.
104 */
105  lsec = 4; /* length of Section 0 */
106 /*
107 ** Get the length of Section 1 and add it to the total.
108 */
109  gets1loc( "LEN1", &iben, &isbyt, &iwid, &wkint[0], 4 );
110  *nmb = lsec + iupm( &bmg[lsec+isbyt-1], &iwid, 3 );
111 /*
112 ** Read up through the end of Section 1.
113 */
114  if ( ( *iret = rbytes( bmg, mxmb, 8, *nmb-8 ) ) != 0 ) return;
115 /*
116 ** Is there a Section 2?
117 */
118  gets1loc( "ISC2", &iben, &isbyt, &iwid, &wkint[0], 4 );
119  nsecs = iupm( &bmg[lsec+isbyt-1], &iwid, 1 ) + 2;
120 /*
121 ** Read up through the end of Section 4.
122 */
123  for ( i = 1; i <= nsecs; i++ ) {
124  if ( ( *iret = rbytes( bmg, mxmb, *nmb, 3 ) ) != 0 ) return;
125  lsec = iupm( &bmg[*nmb], &i24, 3 );
126  if ( ( *iret = rbytes( bmg, mxmb, *nmb+3, lsec-3 ) ) != 0 ) return;
127  *nmb += lsec;
128  }
129 /*
130 ** Read Section 5.
131 */
132  if ( ( *iret = rbytes( bmg, mxmb, *nmb, 4 ) ) != 0 ) return;
133  *nmb += 4;
134 /*
135 ** Expand Section 0 from 4 bytes to 8 bytes, then encode the message length
136 ** and new edition number (i.e. 2) into the new (expanded) Section 0.
137 */
138  if ( *nmb + 4 > *mxmb ) {
139  *iret = 1;
140  return;
141  }
142  memmove( &bmg[8], &bmg[4], *nmb-4 );
143  *nmb += 4;
144  ipkm( &bmg[4], &i3, nmb, 3 );
145  ipkm( &bmg[7], &i1, &i2, 1 );
146  }
147 /*
148 ** Check that the "7777" is in the expected location.
149 */
150  *iret = ( ( ichkstr( "7777", &bmg[*nmb-4], &i4, 4, 4 ) == 0 ) ? 0 : 2 );
151 
152  return;
153 }
Define signatures to enable a number of BUFRLIB subprograms to be called directly from C application ...
FILE * pbf[2]
File pointers.
function iupm(CBAY, NBITS)
THIS FUNCTION UNPACKS AND RETURNS A BINARY INTEGER WORD CONTAINED WITHIN NBITS BITS OF A CHARACTER ST...
Definition: iupm.f:40
function ichkstr(STR, CHR, N)
THIS FUNCTION COMPARES A SPECIFIED NUMBER OF CHARACTERS FROM AN INPUT CHARACTER ARRAY AGAINST THE SAM...
Definition: ichkstr.f:32
subroutine gets1loc(S1MNEM, IBEN, ISBYT, IWID, IRET)
THIS SUBROUTINE RETURNS THE LOCATION (I.E.
Definition: gets1loc.f:80
Define signatures and declare variables for reading or writing BUFR messages via a C language interfa...
f77int rbytes(char *, f77int *, f77int, f77int)
This function reads a specified number of bytes from the system file that was opened via the most rec...
Definition: rbytes.c:40
void crbmg(char *, f77int *, f77int *, f77int *)
This subroutine reads the next BUFR message from the system file that was opened via the most recent ...
Definition: crbmg.c:48
subroutine ipkm(CBAY, NBYT, N)
This subroutine encodes an integer value within a specified number of bytes of a character string...
Definition: ipkm.f:27
subroutine bort(STR)
This subroutine calls subroutine errwrt() to log an error message, then calls subroutine bort_exit() ...
Definition: bort.f:22
function iupbs01(MBAY, S01MNEM)
This function returns a specified value from within Section 0 or Section 1 of a BUFR message...
Definition: iupbs01.f:73