+static int
+cue_enc(const struct buf *b, size_t *offs, enum enc *enc)
+{
+ const char *ln, *eoln, *eoph;
+ size_t sz, phsz, nsz;
+ int i;
+
+ ln = b->buf + (int)*offs;
+ sz = b->sz - *offs;
+
+ /* Look for the end-of-line. */
+
+ if (NULL == (eoln = memchr(ln, '\n', sz)))
+ return(-1);
+
+ /* Set next-line marker. */
+
+ *offs = (size_t)((eoln + 1) - b->buf);
+
+ /* Check if we have the correct header/trailer. */
+
+ if ((sz = (size_t)(eoln - ln)) < 10 ||
+ memcmp(ln, ".\\\" -*-", 7) ||
+ memcmp(eoln - 3, "-*-", 3))
+ return(0);
+
+ /* Move after the header and adjust for the trailer. */
+
+ ln += 7;
+ sz -= 10;
+
+ while (sz > 0) {
+ while (sz > 0 && ' ' == *ln) {
+ ln++;
+ sz--;
+ }
+ if (0 == sz)
+ break;
+
+ /* Find the end-of-phrase marker (or eoln). */
+
+ if (NULL == (eoph = memchr(ln, ';', sz)))
+ eoph = eoln - 3;
+ else
+ eoph++;
+
+ /* Only account for the "coding" phrase. */
+
+ if ((phsz = (size_t)(eoph - ln)) < 7 ||
+ strncasecmp(ln, "coding:", 7)) {
+ sz -= phsz;
+ ln += phsz;
+ continue;
+ }
+
+ sz -= 7;
+ ln += 7;
+
+ while (sz > 0 && ' ' == *ln) {
+ ln++;
+ sz--;
+ }
+ if (0 == sz)
+ break;
+
+ /* Check us against known encodings. */
+
+ for (i = 0; i < ENC__MAX; i++) {
+ nsz = strlen(encs[i].name);
+ if (phsz < nsz)
+ continue;
+ if (strncasecmp(ln, encs[i].name, nsz))
+ continue;
+
+ *enc = (enum enc)i;
+ return(1);
+ }
+
+ /* Unknown encoding. */
+
+ *enc = ENC__MAX;
+ return(1);
+ }
+
+ return(0);
+}
+