📄 pgpprsasc.c
字号:
retval = readLine (ctx, buf, size);
size -= retval;
buf += retval;
written += retval;
if (ctx->eol || ctx->eob)
;
else
break;
/* FALLTHROUGH */
case 125:
ctx->state = 125;
/* Send annotation of raw data if in passthrough mode */
if (ctx->passthrough) {
*error = sendAnnotate (ctx, myself, PGPANN_CLEARDATA,
ctx->armorline, ctx->armorlen);
if (*error)
break;
}
/* FALLTHROUGH */
case 130:
ctx->state = 130;
/*
* Process header line, then back to state armor_header,
* or detect end of headers, and go to state armor_nonheader.
*/
ptr = ctx->armorline;
lineused = ctx->armorlen;
/* Skip past prefix from "-----BEGIN PGP" if it matches */
if (ctx->skipPrefixLength > 0 &&
(PGPSize)lineused > ctx->skipPrefixLength &&
0 == memcmp (ptr, ctx->skipPrefix, ctx->skipPrefixLength)) {
ptr += ctx->skipPrefixLength;
lineused -= ctx->skipPrefixLength;
}
/* Find trailing white space... */
while (lineused && isspace (ptr[lineused - 1]))
lineused--;
ctx->noarmorblanks = FALSE;
if (lineused) {
int err;
/* temporarily null-terminate this string */
temp_c = ptr[lineused];
ptr[lineused] = '\0';
/*
* Change states once we see a non-header line. This is
* now the only way of changing to the state where we are
* parsing the ascii armor. It deals with the case where
* there are no blanks between the headers and the armored
* portion, as well as the normal case where there is a blank
* line, and also munging which inserts blank lines.
*/
if( validArmorLine( ptr, lineused ) ) {
ptr[lineused] = temp_c;
ctx->noarmorblanks = TRUE;
goto state_pgp_armor_nonheader;
}
err = parseHeader (ctx, ptr, lineused);
if (err) {
*error = sendAnnotate (ctx, myself,
PGPANN_ARMOR_BADHEADER,
ctx->armorline,
lineused);
ptr[lineused] = temp_c;
if (*error)
break;
/* XXX: Ignore bad headers? */
}
goto state_pgp_armor_header;
}
/*
* No longer change states on blank lines. Instead use
* the validArmorLine test above. This deals with the munging
* done by Eudora which makes every other line a blank line.
*/
goto state_pgp_armor_header;
/* Not reached */
/* FALLTHROUGH */
case 150:
state_pgp_armor_nonheader:
ctx->state = 150;
/* get the message and part information */
if (!ctx->part) {
/* This is true for all normal armor messages */
msg = getMessage (ctx, ctx->messageid, ctx->maxparts);
if (!msg) {
/* This is an error */
*error = kPGPError_OutOfMemory;
break;
}
part = getPart (ctx, msg, ctx->thispart);
if (!part) {
/* This is an error too */
*error = kPGPError_OutOfMemory;
break;
}
ctx->part = part;
}
/* FALLTHROUGH */
case 160:
ctx->state = 160;
/*
* Either try to make the message writable or send an
* annotation saying we have a message part.
*/
msg = ctx->part->msg;
if (ctx->thispart == 1) {
*error = writeMessage (ctx, msg);
if (*error)
break;
} else {
PGPByte *b;
b = (PGPByte *)pgpContextMemAlloc( cdkContext,
kPGPPrsAscCmdBufSize, kPGPMemoryMgrFlags_Clear);
if (b == NULL)
{
*error = kPGPError_OutOfMemory;
break;
}
i = 0;
memcpy (b, &ctx->thispart, sizeof (ctx->thispart));
i += sizeof (ctx->thispart);
memcpy (b+i, &ctx->maxparts, sizeof (ctx->maxparts));
i += sizeof (ctx->maxparts);
memcpy (b+i, ctx->messageid,
strlen (ctx->messageid));
i += strlen (ctx->messageid);
*error = sendAnnotate (ctx, myself, PGPANN_ARMOR_PART,
b, i);
pgpContextMemFree( cdkContext, b);
if (*error)
break;
}
/* If we had no blank lines, we already have an armor buffer */
if( ctx->noarmorblanks ) {
ctx->noarmorblanks = FALSE;
goto state_pgp_armor_line;
}
/* FALLTHROUGH */
case 170:
state_pgp_armor_loop:
ctx->state = 170;
/* read until EOL to get to end of the last line */
ctx->armorptr = ctx->armorline;
ctx->armorlen = 0;
while (ctx->eol != 1) {
ctx->armorlen = 0;
retval = readLine (ctx, buf, size);
written += retval;
buf += retval;
size -= retval;
if (!size)
return written;
}
ctx->eol = 0;
ctx->eob = 0;
ctx->armorlen = 0;
/* FALLTHROUGH */
case 180:
ctx->state = 180;
/* call readline until we have EOB or EOL */
retval = readLine (ctx, buf, size);
size -= retval;
buf += retval;
written += retval;
if (ctx->eol || ctx->eob)
;
else
break;
/* FALLTHROUGH */
case 185:
ctx->state = 185;
/* Send annotation of raw data if in passthrough mode */
if (ctx->passthrough) {
*error = sendAnnotate (ctx, myself, PGPANN_CLEARDATA,
ctx->armorline, ctx->armorlen);
if (*error)
break;
}
/* FALLTHROUGH */
case 190:
state_pgp_armor_line:
ctx->state = 190;
/*
* make sure this is not a CRC line. If it is a CRC
* then goto state armor_crc. if it is not a CRC line, then
* it must be an armorline. So, process it as an
* armor line and then fallthrough to next state to
* output it.
*/
ptr = ctx->armorline;
inlen = ctx->armorlen;
/* Skip past prefix from "-----BEGIN PGP" if it matches */
if (ctx->skipPrefixLength > 0 && inlen >= ctx->skipPrefixLength &&
0 == memcmp (ptr, ctx->skipPrefix, ctx->skipPrefixLength)) {
ptr += ctx->skipPrefixLength;
inlen -= ctx->skipPrefixLength;
}
if (ptr[0] == '=') {
/* This looks like a CRC */
goto state_pgp_armor_crc;
}
/* find the end of the armorline */
while (inlen && isspace (ptr[inlen - 1]))
inlen--;
/* check the length of the armorline */
if (inlen > 80) {
*error = sendAnnotate (ctx, myself,
PGPANN_ARMOR_TOOLONG,
ctx->armorline, ctx->armorlen);
if (*error)
break;
goto state_pgp_finish;
}
if (inlen == 0) {
/* Blank lines are just skipped, some mailers put blanks in */
goto state_pgp_armor_loop;
}
/* Make sure we're not expecting a CRC */
if (inlen >= 9 && ptr[inlen-5] == '=') {
/* Handle CRC at end of armor line */
ctx->crcendline = TRUE;
i = pgpDearmorLine (ptr, ctx->databuf, inlen - 5);
} else {
i = pgpDearmorLine (ptr, ctx->databuf, inlen);
}
if (i < 1 || i > 60) {
/* error in deamorline */
#if 555
printf("PGPANN_ARMOR_BADLINE error\n");
#endif 555
*error = sendAnnotate (ctx, myself,
PGPANN_ARMOR_BADLINE,
ctx->armorline, ctx->armorlen);
if (*error)
break;
goto state_pgp_finish;
}
ctx->crc = crcUpdate (ctx->crc, ctx->databuf, i);
ctx->datalen = i;
ctx->dataptr = ctx->databuf;
/* FALLTHROUGH */
case 200:
ctx->state = 200;
/* output the dearmored data, then goto state armor_loop */
/* But check for CRC on end of armor line and to armor_crc if so */
part = ctx->part;
while (ctx->datalen) {
retval = writePartData (part, ctx->dataptr,
ctx->datalen, error);
ctx->dataptr += retval;
ctx->datalen -= retval;
if (*error)
return written;
}
/* If had CRC at end of last armor line, go process it now */
if (ctx->crcendline) {
ctx->crcendline = FALSE;
goto state_pgp_armor_crc;
}
goto state_pgp_armor_loop;
case 210:
state_pgp_armor_crc:
ctx->state = 210;
/* Deal with CRC */
ptr = ctx->armorline;
inlen = ctx->armorlen;
/* Skip past prefix from "-----BEGIN PGP" if it matches */
if (ctx->skipPrefixLength > 0 && inlen >= ctx->skipPrefixLength &&
0 == memcmp (ptr, ctx->skipPrefix, ctx->skipPrefixLength)) {
ptr += ctx->skipPrefixLength;
inlen -= ctx->skipPrefixLength;
}
/* find the end of the armorline */
while (inlen && isspace (ptr[inlen - 1]))
inlen--;
if (ptr[0] != '=') {
/* Must be CRC at end of line */
pgpAssert(inlen >= 9 && ptr[inlen-5] == '=');
ptr += inlen - 5;
inlen = 5;
}
crc = dearmorCrc (ptr, inlen);
if (crc < 0) {
/* error */
*error = sendAnnotate (ctx, myself,
PGPANN_ARMOR_CRCCANT,
ctx->armorline, ctx->armorlen);
if (*error)
break;
goto state_pgp_finish;
}
if ((PGPUInt32)crc != ctx->crc) {
/* mismatch */
*error = sendAnnotate (ctx, myself,
PGPANN_ARMOR_CRCBAD,
ctx->armorline, ctx->armorlen);
if (*error)
break;
goto state_pgp_finish;
}
/* FALLTHROUGH */
case 220:
state_pgp_armor_end_loop:
ctx->state = 220;
/* read until EOL to get to end of the last line */
ctx->armorptr = ctx->armorline;
ctx->armorlen = 0;
while (ctx->eol != 1) {
ctx->armorlen = 0;
retval = readLine (ctx, buf, size);
written += retval;
buf += retval;
size -= retval;
if (!size)
return written;
}
ctx->eol = 0;
ctx->eob = 0;
ctx->armorlen = 0;
/* FALLTHROUGH */
case 230:
ctx->state = 230;
/* call readline until we have EOB or EOL */
retval = readLine (ctx, buf, size);
size -= retval;
buf += retval;
written += retval;
if (ctx->eol || ctx->eob)
;
else
break;
/* FALLTHROUGH */
case 235:
ctx->state = 235;
/* Send annotation of raw data if in passthrough mode */
if (ctx->passthrough) {
*error = sendAnnotate (ctx, myself, PGPANN_CLEARDATA,
ctx->armorline, ctx->armorlen);
if (*error)
break;
}
/* FALLTHROUGH */
case 240:
ctx->state = 240;
/* check for END */
ptr = ctx->armorline;
inlen = ctx->armorlen;
/* Skip past prefix from "-----BEGIN PGP" if it matches */
if (ctx->skipPrefixLength > 0 && inlen >= ctx->skipPrefixLength &&
0 == memcmp (ptr, ctx->skipPrefix, ctx->skipPrefixLength)) {
ptr += ctx->skipPrefixLength;
inlen -= ctx->skipPrefixLength;
}
/* ignore blank line here */
while (inlen && isspace (ctx->armorline[inlen - 1]))
inlen--;
if (inlen==0) {
goto state_pgp_armor_end_loop;
}
/* Look for END PGP line */
if (inlen < sizeof (prefix3) - 1 ||
memcmp (ptr, prefix3, sizeof (prefix3) - 1)) {
/* missing end -- do what???
* keep looking for it, that's what!
* Stuck-in lines before END go into non-pgp segment,
* along with END line, causing confusion.
*/
goto state_pgp_armor_end_loop;
}
#if MIMEPARSE
if (ctx->mime_signed) {
/* Special cleanup for MIME, wait for final boundary */
goto state_pgpmime_sig_end;
}
#endif
/* FALLTHROUGH */
case 250:
ctx->state = 250;
/* read until EOL to get to end of the last line */
ctx->armorptr = ctx->armorline;
ctx->armorlen = 0;
while (ctx->eol != 1) {
ctx->armorlen = 0;
retval = readLine (ctx, buf, size);
written += retval;
buf += retval;
size -= retval;
if (!size)
return written;
}
/* FALLTHROUGH */
case 260:
state_pgp_finish:
ctx->state = 260;
/*
* finish this part, send an end annotation if we need
* to, then clear
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -