接收浏览器上传文件的cgi程序

**************************************************************************
2007-1-5 11:42 establish by lzh.A cgi program.
get a file from user's explorer.
***************************************************************************/
#include <stdio.h>
#include <string.h>

#define DEAL_BUF_LEN  1024
#define SIGN_CODE_LEN  100
#define FILE_NAME_LEN 64
#define FILE_SAVE_DIR "/var/log/"
enum
{
 STATE_START,
 STATE_GET_SIGN_CODE,
 STATE_GET_FILE_NAME,
 STATE_GET_FILE_START,
 STATE_GET_FILE_CONTENT,
 STATE_CHECK_END,
 STATE_END
};
/***************************************************************************
ShowErrorInfo
****************************************************************************/
static void ShowErrorInfo(char * error)
{

 printf("Content-type:text/plain/n/n");
 printf(error);
}

/* 主体从这里开始 */

int main(void)
{
 FILE *fp; /* 文件指针,保存我们要获得的文件 */
 int getState = STATE_START;
 int contentLength;/*标准输入内容长度*/
 int nowReadLen;
 int signCodeLen;
 int tmpLen;
 char *nowReadP;
 char *nowWriteP;
 char dealBuf[DEAL_BUF_LEN];
 char signCode[SIGN_CODE_LEN]; /*存储本次的特征码*/
 char tmpSignCode[SIGN_CODE_LEN];
 char fileName[FILE_NAME_LEN];
 memset(dealBuf,0,DEAL_BUF_LEN);
 memset(signCode,0,SIGN_CODE_LEN);
 memset(fileName,0,FILE_NAME_LEN);
 nowReadLen = 0;
 if((char *)getenv("CONTENT_LENGTH")!=NULL)
 {
  contentLength = atoi((char *)getenv("CONTENT_LENGTH"));
 }
 else
 {
  ShowErrorInfo("没有数据!");
  exit(1);
 }
 
 while(contentLength > 0)
 {
  if(contentLength >= DEAL_BUF_LEN)
  {
   nowReadLen = DEAL_BUF_LEN;
  }
  else
  {
   nowReadLen = contentLength;
  }
  contentLength -= nowReadLen;
  if(fread(dealBuf,sizeof(char),nowReadLen,stdin) != nowReadLen)
  {
   ShowErrorInfo("读取数据错误!");
   exit(1);
  }
  nowReadP = dealBuf;
  while(nowReadLen > 0)
  {
   switch (getState)
   {
    case STATE_START:
     nowWriteP = signCode;
     getState = STATE_GET_SIGN_CODE;
    case STATE_GET_SIGN_CODE:
     if(strncmp(nowReadP,"/r/n",2) == 0)
     {
      signCodeLen = nowWriteP - signCode;
      nowReadP++;
      nowReadLen--;
      *nowWriteP = 0;
      getState = STATE_GET_FILE_NAME;
      //ShowErrorInfo(signCode);
     }
     else
     {
      *nowWriteP = *nowReadP;
      nowWriteP++;
     }
     break;
    case STATE_GET_FILE_NAME:
     if(strncmp(nowReadP,"filename=",strlen("filename=")) == 0)
     {
      nowReadP += strlen("filename=");
      nowReadLen -= strlen("filename=");
      nowWriteP = fileName + strlen(FILE_SAVE_DIR);
      while(*nowReadP != '/r')
      {
       if(*nowReadP == '//')
       {
        nowWriteP = fileName + strlen(FILE_SAVE_DIR);
       }
       else if(*nowReadP != '/"')
       {
        *nowWriteP = *nowReadP;
        nowWriteP++;
       }
       nowReadP++;
       nowReadLen--;
      }
      *nowWriteP = 0;
      nowReadP++;
      nowReadLen--;
      getState = STATE_GET_FILE_START;
      memcpy(fileName,FILE_SAVE_DIR,strlen(FILE_SAVE_DIR));
      if((fp=fopen(fileName,"w"))==NULL)
      {
       fprintf(stderr,"open file error/n");
       exit(1);
      }
      //ShowErrorInfo(fileName);
     }
     break;
    case STATE_GET_FILE_START:
     if(strncmp(nowReadP,"/r/n/r/n",4) == 0)
     {
      nowReadP += 3;
      nowReadLen -= 3;
      getState = STATE_GET_FILE_CONTENT;
      //ShowErrorInfo("get");
     }
     break;
    case STATE_GET_FILE_CONTENT:
     if(*nowReadP != '/r')
     {
      fputc(*nowReadP,fp);
     }
     else
     {
      if(nowReadLen >= (signCodeLen + 2))
      {
       if(strncmp(nowReadP + 2,signCode,signCodeLen) == 0)
       {
        getState = STATE_END;
        nowReadLen = 1;
        ShowErrorInfo("传输完成");
       }
       else
       {
        fputc(*nowReadP,fp);
       }
      }
      else
      {
       getState = STATE_CHECK_END;
       nowWriteP = tmpSignCode;
       *nowWriteP = *nowReadP;
       nowWriteP++;
       tmpLen = 1;
      }
     }
     break;
    case STATE_CHECK_END:
     if(*nowReadP != '/r')
     {
      if(tmpLen < signCodeLen + 2)
      {
       *nowWriteP = *nowReadP;
       nowWriteP++;
       tmpLen++;
       if(tmpLen == signCodeLen + 2)
       {
        *nowWriteP = 0;
        if((tmpSignCode[1] == '/n')&&(strncmp(tmpSignCode + 2,signCode,signCodeLen) == 0))
        {
         getState = STATE_END;
         nowReadLen = 1;
         ShowErrorInfo("传输完成");
        }
        else
        {
         //fprintf(fp,tmpSignCode);
         fwrite(tmpSignCode,sizeof(char),tmpLen,fp);
         getState = STATE_GET_FILE_CONTENT;
        }
       }
      }
     }
     else
     {
      *nowWriteP = 0;
      //fprintf(fp,tmpSignCode);
      fwrite(tmpSignCode,sizeof(char),tmpLen,fp);
      nowWriteP = tmpSignCode;
      *nowWriteP = *nowReadP;
      nowWriteP++;
      tmpLen = 1;
     }
     break;
    case STATE_END:
     nowReadLen = 1;
     break;
    default:break;
   }
   nowReadLen--;
   nowReadP++;
  }
 }
 if(fp != NULL)
 {
  fclose(fp);
 }
 return 0;
}
 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值