fdtype sp_openserport(char *dev, int baud) { fdtype fd; #if IS_WINDOWS char *dev2 = dev; if ((strlen(dev) > 3) && (tolower((unsigned char)dev[0]) == 'c') && (tolower((unsigned char)dev[1]) == 'o') && (tolower((unsigned char)dev[2]) == 'm')) { dev2 = malloc(strlen(dev) + 5); if (!dev2) { msg_perr_strerror("Out of memory: "); return SER_INV_FD; } strcpy(dev2, "\\\\.\\"); strcpy(dev2 + 4, dev); } fd = CreateFile(dev2, GENERIC_READ | GENERIC_WRITE, 0, NULL, OPEN_EXISTING, 0, NULL); if (dev2 != dev) free(dev2); if (fd == INVALID_HANDLE_VALUE) { msg_perr_strerror("Cannot open serial port: "); return SER_INV_FD; } if (serialport_config(fd, baud) != 0) { CloseHandle(fd); return SER_INV_FD; } return fd; #else fd = open(dev, O_RDWR | O_NOCTTY | O_NDELAY); // Use O_NDELAY to ignore DCD state if (fd < 0) { msg_perr_strerror("Cannot open serial port: "); return SER_INV_FD; } /* Ensure that we use blocking I/O */ const int flags = fcntl(fd, F_GETFL); if (flags == -1) { msg_perr_strerror("Could not get serial port mode: "); goto err; } if (fcntl(fd, F_SETFL, flags & ~O_NONBLOCK) != 0) { msg_perr_strerror("Could not set serial port mode to blocking: "); goto err; } if (serialport_config(fd, baud) != 0) { goto err; } return fd; err: close(fd); return SER_INV_FD; #endif }
//对STC15系列的芯片进行数据下载程序 static int Firmware_Download(BYTE *pdat, long size) { BYTE arg; BYTE cnt; WORD addr; Initial(); //握手 CommInit(); while (1) { if (UartRecvStep == 0) { UartSend(0x7f); DelayXms(10); } if (UartReceived) { arg = RxBuffer[4]; if (RxBuffer[0] == 0x50) break; return eDownloadErrCodeHandshake; } if (TimeOut == 0) { printf("waiting for mcu isp timeout\n"); return eDownloadErrCodeTimeout; } } printf("set comm param\n"); //设置参数 TxBuffer[0] = 0x01; TxBuffer[1] = arg; TxBuffer[2] = 0x40; TxBuffer[3] = HIBYTE(RL(MAXBAUD)); TxBuffer[4] = LOBYTE(RL(MAXBAUD)); TxBuffer[5] = 0x00; TxBuffer[6] = 0x00; TxBuffer[7] = 0xc3; CommSend(8); while (1) { if (TimeOut == 0) return eDownloadErrCodeTimeout; if (UartReceived) { if (RxBuffer[0] == 0x01) break; return eDownloadErrCodeSetCommParam; } } printf("download prepare \n"); //准备 serialport_config(handle_download_port,MAXBAUD,8,1,'e'); DelayXms(10); TxBuffer[0] = 0x05; CommSend(1); while (1) { if (TimeOut == 0) return eDownloadErrCodeTimeout; if (UartReceived) { if (RxBuffer[0] == 0x05) break; return eDownloadErrCodeSetCommParam; } } printf("erase flash ...\n"); //擦除 DelayXms(10); TxBuffer[0] = 0x03; TxBuffer[1] = 0x00; CommSend(2); TimeOut = 100; while (1) { if (TimeOut == 0) return eDownloadErrCodeTimeout; if (UartReceived) { if (RxBuffer[0] == 0x03) break; return eDownloadErrCodeEraseFlash; } } printf("program flash size[0x%lx]...\n",size); //写用户代码 DelayXms(10); addr = 0; TxBuffer[0] = 0x22; while (addr < size) { TxBuffer[1] = HIBYTE(addr); TxBuffer[2] = LOBYTE(addr); cnt = 0; while (addr < size) { TxBuffer[cnt+3] = pdat[addr]; addr++; cnt++; if (cnt >= 128) break; } CommSend(cnt + 3); while (1) { if (TimeOut == 0) return eDownloadErrCodeTimeout; if (UartReceived) { if ((RxBuffer[0] == 0x02) && (RxBuffer[1] == 'T')) break; return eDownloadErrCodeProgramFlash; } } TxBuffer[0] = 0x02; } printf("program hardware option ... skipped\n"); #if 0 //写硬件选项(如果不需要修改硬件选项,此步骤可直接跳过) DelayXms(10); for (cnt=0; cnt<128; cnt++) { TxBuffer[cnt] = 0xff; } //Do we know details of hardware options??? TxBuffer[0] = 0x04; TxBuffer[1] = 0x00; TxBuffer[2] = 0x00; TxBuffer[34] = 0xfd; TxBuffer[62] = arg; TxBuffer[63] = 0x7f; TxBuffer[64] = 0xf7; TxBuffer[65] = 0x7b; TxBuffer[66] = 0x1f; CommSend(67); while (1) { if (TimeOut == 0) return eDownloadErrCodeTimeout; if (UartReceived) { if ((RxBuffer[0] == 0x04) && (RxBuffer[1] == 'T')) break; return eDownloadErrCodeProgramOption; } } #endif //下载完成 return eDownloadErrCodeSuccess; }
static void Initial(void) { //串口数据模式必须为8位数据+1位偶检验 serialport_config(handle_download_port,MINBAUD,8,1,'e'); }