+/* decFloatFromPackedChecked -- set from exponent and packed; checked */
+/* */
+/* df is the target decFloat */
+/* exp is the in-range unbiased exponent, q, or a special value in */
+/* the form returned by decFloatGetExponent */
+/* packed holds DECPMAX packed decimal digits plus a sign nibble */
+/* (all 6 codes are OK); the first (MSD) must be 0 if df is a NaN */
+/* and all digits must be 0 if df is infinite. For DOUBLE and */
+/* QUAD the first (pad) nibble must be 0. */
+/* All coefficient nibbles must be in 0-9 and sign in A-F. */
+/* returns df, which will be canonical or NULL if any of the */
+/* requirements are not met (if this case df is unchanged); that */
+/* is, the input data must be as returned by decFloatToPacked, */
+/* except that all six sign codes are accepted. */
+/* */
+/* No status will be set. */
+/* ------------------------------------------------------------------ */
+decFloat * decFloatFromPackedChecked(decFloat *df, Int exp,
+ const uByte *packed) {
+ uByte bcdar[DECPMAX+2]; /* work [+1 for pad, +1 for sign] */
+ const uByte *ip; /* .. */
+ uByte *op; /* .. */
+ Int sig=0; /* sign */
+
+ /* expand coefficient and sign to BCDAR */
+ #if SINGLE
+ op=bcdar+1; /* no pad digit */
+ #else
+ op=bcdar; /* first (pad) digit here */
+ #endif
+ for (ip=packed; ip<packed+((DECPMAX+2)/2); ip++) {
+ *op=*ip>>4;
+ if (*op>9) return NULL;
+ op++;
+ *op=(uByte)(*ip&0x0f); /* [final nibble is sign] */
+ if (*op>9 && ip<packed+((DECPMAX+2)/2)-1) return NULL;
+ op++;
+ }
+ op--; /* -> sign byte */
+ if (*op<=9) return NULL; /* bad sign */
+ if (*op==DECPMINUS || *op==DECPMINUSALT) sig=DECFLOAT_Sign;
+
+ #if !SINGLE
+ if (bcdar[0]!=0) return NULL; /* bad pad nibble */
+ #endif
+
+ if (EXPISNAN(exp)) { /* a NaN */
+ if (bcdar[1]!=0) return NULL; /* bad msd */
+ } /* NaN */
+ else if (EXPISINF(exp)) { /* is infinite */
+ Int i;
+ for (i=0; i<DECPMAX; i++) {
+ if (bcdar[i+1]!=0) return NULL; /* should be all zeros */
+ }
+ } /* infinity */
+ else { /* finite */
+ /* check the exponent is in range */
+ if (exp>DECEMAX-DECPMAX+1) return NULL;
+ if (exp<DECEMIN-DECPMAX+1) return NULL;
+ }
+ return decFloatFromBCD(df, exp, bcdar+1, sig);
+ } /* decFloatFromPacked */
+
+/* ------------------------------------------------------------------ */
+/* decFloatFromString -- conversion from numeric string */