STM32F030 IIC2通用读写24C02、24C16、24C32、24C64等例程
前言:
咱们做嵌入式开发经常用到EEPROM,但是EEPROM的大小不同会需要不同代码来适配,这不利于快捷开发。在此本人分享自己优化总结后一段代码给大家,该代码通用读写24C02、24C16、24C32、24C64等EEPROM,只需在宏定义做相应芯片型号定义,则可使用。
注意!该代码适用于STM32F030的I2C2,如果需要用I2C1或者芯片型号是STM32F0XX其他系列的,需要做相应的驱动代码改动。
C文件代码:
/* Includes ------------------------------------------------------------------*/
#include "bs_iic.h"uint32_t AT24Cxx_Timeout;
uint8_t AT24Cxx_Address=0;
uint8_t AT24Cxx_DataNum=0;/*
主机模式
普通模式 100kHZ
I2C时钟频率32000KHz
使用模拟滤波器
不使用数字滤波器
上升时间100ns
下降时间10ns
*/
uint32_t AT24Cxx_TIMEOUT_UserCallback(void)
{/* Block communication and all processes *//* while (1){ }*/return AT24Cxx_FAIL;
}void I2C2_Init(void)
{I2C_InitTypeDef I2C_InitStruct;GPIO_InitTypeDef GPIO_InitStructure;I2C_DeInit(I2C1);//RCC_I2CCLKConfig(RCC_I2C1CLK_SYSCLK);RCC_AHBPeriphClockCmd(RCC_AHBPeriph_GPIOB, ENABLE);GPIO_InitStructure.GPIO_Pin = GPIO_Pin_10 | GPIO_Pin_11;GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;GPIO_InitStructure.GPIO_OType = GPIO_OType_OD;
// GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL;GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;GPIO_Init(GPIOB, &GPIO_InitStructure);GPIO_PinAFConfig(GPIOB, GPIO_PinSource10, GPIO_AF_1);GPIO_PinAFConfig(GPIOB, GPIO_PinSource11, GPIO_AF_1);RCC_APB1PeriphClockCmd(RCC_APB1Periph_I2C2, ENABLE);I2C_InitStruct.I2C_Ack=I2C_Ack_Enable;I2C_InitStruct.I2C_AcknowledgedAddress=I2C_AcknowledgedAddress_7bit;I2C_InitStruct.I2C_AnalogFilter=I2C_AnalogFilter_Enable;I2C_InitStruct.I2C_DigitalFilter=0x00;I2C_InitStruct.I2C_Mode=I2C_Mode_I2C;I2C_InitStruct.I2C_OwnAddress1=0x00;//0x55;//I2C_InitStruct.I2C_Timing=0x30E32E44;//0x20D22E37;I2C_Init(I2C2,&I2C_InitStruct);//RCC_I2CCLKConfig(RCC_I2C1CLK_SYSCLK);I2C_Cmd(I2C2, ENABLE);
}void AT24CXX_Init(void)
{I2C2_Init();AT24Cxx_Address = AT24Cxx_HW_Address;
}uint32_t AT24Cxx_WaitEepromStandbyState(void)
{__IO uint32_t sEETrials = 0;/* Configure CR2 register : set Slave Address and end mode */I2C_TransferHandling(AT24Cxx_I2C, AT24Cxx_Address,0, I2C_AutoEnd_Mode,I2C_No_StartStop); do{ /* Initialize sEETimeout */AT24Cxx_Timeout = AT24Cxx_FLAG_TIMEOUT;/* Clear NACKF */I2C_ClearFlag(AT24Cxx_I2C, I2C_ICR_NACKCF | I2C_ICR_STOPCF);/* Generate start */I2C_GenerateSTART(AT24Cxx_I2C, ENABLE);/* Wait until timeout elapsed */while (AT24Cxx_Timeout-- != 0); /* Check if the maximum allowed numbe of trials has bee reached */if (sEETrials++ == AT24Cxx_MAX_TRIALS_NUMBER){/* If the maximum number of trials has been reached, exit the function */return AT24Cxx_TIMEOUT_UserCallback();}}while(I2C_GetFlagStatus(AT24Cxx_I2C, I2C_ISR_NACKF) != RESET);/* Clear STOPF */I2C_ClearFlag(AT24Cxx_I2C, I2C_ICR_STOPCF);/* Return sEE_OK if device is ready */return AT24Cxx_OK;
}uint32_t AT24Cxx_WritePage(uint8_t* pBuffer, uint16_t WriteAddr, uint8_t* NumByteToWrite)
{uint32_t DataNum = 0;
#if defined(AT24C04) || defined(AT24C08)|| defined(AT24C16) || defined(AT24C32)|| defined(AT24C64) I2C_TransferHandling(AT24Cxx_I2C, AT24Cxx_Address, 2, I2C_Reload_Mode, I2C_Generate_Start_Write);
#elseI2C_TransferHandling(AT24Cxx_I2C, AT24Cxx_Address, 1, I2C_Reload_Mode, I2C_Generate_Start_Write);
#endifAT24Cxx_Timeout = AT24Cxx_LONG_TIMEOUT;while(I2C_GetFlagStatus(AT24Cxx_I2C, I2C_ISR_TXIS) == RESET){if((AT24Cxx_Timeout--) == 0) {return AT24Cxx_TIMEOUT_UserCallback();}}#if defined(AT24C04) || defined(AT24C08)|| defined(AT24C16) || defined(AT24C32)|| defined(AT24C64) /* Send MSB of memory address */I2C_SendData(AT24Cxx_I2C, (uint8_t)((WriteAddr & 0xFF00) >> 8)); /* Wait until TXIS flag is set */AT24Cxx_Timeout = AT24Cxx_LONG_TIMEOUT;while(I2C_GetFlagStatus(AT24Cxx_I2C, I2C_ISR_TXIS) == RESET){if((AT24Cxx_Timeout--) == 0) {return AT24Cxx_TIMEOUT_UserCallback();}}
#endif/* Send LSB of memory address */I2C_SendData(AT24Cxx_I2C, (uint8_t)(WriteAddr & 0x00FF));/* Wait until TCR flag is set */AT24Cxx_Timeout = AT24Cxx_LONG_TIMEOUT;while(I2C_GetFlagStatus(AT24Cxx_I2C, I2C_ISR_TCR) == RESET){if((AT24Cxx_Timeout--) == 0) {return AT24Cxx_TIMEOUT_UserCallback();}}/* Update CR2 : set Slave Address , set write request, generate Start and set end mode */I2C_TransferHandling(AT24Cxx_I2C, AT24Cxx_Address, (uint8_t)(*NumByteToWrite), I2C_AutoEnd_Mode, I2C_No_StartStop);while (DataNum != (*NumByteToWrite)){ /* Wait until TXIS flag is set */AT24Cxx_Timeout = AT24Cxx_LONG_TIMEOUT;while(I2C_GetFlagStatus(AT24Cxx_I2C, I2C_ISR_TXIS) == RESET){if((AT24Cxx_Timeout--) == 0) {return AT24Cxx_TIMEOUT_UserCallback();}} /* Write data to TXDR */I2C_SendData(AT24Cxx_I2C, (uint8_t)(pBuffer[DataNum]));/* Update number of transmitted data */DataNum++; } /* Wait until STOPF flag is set */AT24Cxx_Timeout = AT24Cxx_LONG_TIMEOUT;while(I2C_GetFlagStatus(AT24Cxx_I2C, I2C_ISR_STOPF) == RESET){if((AT24Cxx_Timeout--) == 0) {return AT24Cxx_TIMEOUT_UserCallback();}} /* Clear STOPF flag */I2C_ClearFlag(AT24Cxx_I2C, I2C_ICR_STOPCF);return AT24Cxx_OK;
}void AT24Cxx_WriteBuffer(uint8_t* pBuffer, uint16_t WriteAddr, uint16_t NumByteToWrite)
{uint16_t NumOfPage = 0, NumOfSingle = 0, count = 0;uint16_t Addr = 0;Addr = WriteAddr % AT24Cxx_PAGESIZE;count = AT24Cxx_PAGESIZE - Addr;NumOfPage = NumByteToWrite / AT24Cxx_PAGESIZE;NumOfSingle = NumByteToWrite % AT24Cxx_PAGESIZE;/*!< If WriteAddr is sEE_PAGESIZE aligned */if(Addr == 0) {/*!< If NumByteToWrite < sEE_PAGESIZE */if(NumOfPage == 0) {/* Store the number of data to be written */AT24Cxx_DataNum = NumOfSingle;/* Start writing data */AT24Cxx_WritePage(pBuffer, WriteAddr, (uint8_t*)(&AT24Cxx_DataNum));AT24Cxx_WaitEepromStandbyState();}/*!< If NumByteToWrite > sEE_PAGESIZE */else {while(NumOfPage--){/* Store the number of data to be written */AT24Cxx_DataNum = AT24Cxx_PAGESIZE; AT24Cxx_WritePage(pBuffer, WriteAddr, (uint8_t*)(&AT24Cxx_DataNum)); AT24Cxx_WaitEepromStandbyState();WriteAddr += AT24Cxx_PAGESIZE;pBuffer += AT24Cxx_PAGESIZE;}if(NumOfSingle!=0){/* Store the number of data to be written */AT24Cxx_DataNum = NumOfSingle; AT24Cxx_WritePage(pBuffer, WriteAddr, (uint8_t*)(&AT24Cxx_DataNum));AT24Cxx_WaitEepromStandbyState();}}}/*!< If WriteAddr is not sEE_PAGESIZE aligned */else {/*!< If NumByteToWrite < sEE_PAGESIZE */if(NumOfPage== 0) {/*!< If the number of data to be written is more than the remaining space in the current page: */if (NumByteToWrite > count){/* Store the number of data to be written */AT24Cxx_DataNum = count; /*!< Write the data conained in same page */AT24Cxx_WritePage(pBuffer, WriteAddr, (uint8_t*)(&AT24Cxx_DataNum));AT24Cxx_WaitEepromStandbyState(); /* Store the number of data to be written */AT24Cxx_DataNum = (NumByteToWrite - count); /*!< Write the remaining data in the following page */AT24Cxx_WritePage((uint8_t*)(pBuffer + count), (WriteAddr + count), (uint8_t*)(&AT24Cxx_DataNum));AT24Cxx_WaitEepromStandbyState(); } else {/* Store the number of data to be written */AT24Cxx_DataNum = NumOfSingle; AT24Cxx_WritePage(pBuffer, WriteAddr, (uint8_t*)(&AT24Cxx_DataNum));AT24Cxx_WaitEepromStandbyState(); } }/*!< If NumByteToWrite > sEE_PAGESIZE */else{NumByteToWrite -= count;NumOfPage = NumByteToWrite / AT24Cxx_PAGESIZE;NumOfSingle = NumByteToWrite % AT24Cxx_PAGESIZE;if(count != 0){ /* Store the number of data to be written */AT24Cxx_DataNum = count; AT24Cxx_WritePage(pBuffer, WriteAddr, (uint8_t*)(&AT24Cxx_DataNum));AT24Cxx_WaitEepromStandbyState();WriteAddr += count;pBuffer += count;} while(NumOfPage--){/* Store the number of data to be written */AT24Cxx_DataNum = AT24Cxx_PAGESIZE; AT24Cxx_WritePage(pBuffer, WriteAddr, (uint8_t*)(&AT24Cxx_DataNum));AT24Cxx_Timeout = AT24Cxx_LONG_TIMEOUT;AT24Cxx_WaitEepromStandbyState();WriteAddr += AT24Cxx_PAGESIZE;pBuffer += AT24Cxx_PAGESIZE; }if(NumOfSingle != 0){/* Store the number of data to be written */AT24Cxx_DataNum = NumOfSingle; AT24Cxx_WritePage(pBuffer, WriteAddr, (uint8_t*)(&AT24Cxx_DataNum)); AT24Cxx_WaitEepromStandbyState();}}}
}uint32_t AT24Cxx_ReadBuffer(uint8_t* pBuffer, uint16_t ReadAddr, uint16_t* NumByteToRead)
{ uint32_t NumbOfSingle = 0, Count = 0, DataNum = 0, StartCom = 0;/* Get number of reload cycles */Count = (*NumByteToRead) / 255; NumbOfSingle = (*NumByteToRead) % 255;
#if defined(AT24C04) || defined(AT24C08)|| defined(AT24C16) || defined(AT24C32)|| defined(AT24C64) /* Configure slave address, nbytes, reload and generate start */I2C_TransferHandling(AT24Cxx_I2C, AT24Cxx_Address, 2, I2C_SoftEnd_Mode, I2C_Generate_Start_Write);
#elseI2C_TransferHandling(AT24Cxx_I2C, AT24Cxx_Address, 1, I2C_SoftEnd_Mode, I2C_Generate_Start_Write);
#endif/* Wait until TXIS flag is set */AT24Cxx_Timeout = AT24Cxx_LONG_TIMEOUT;while(I2C_GetFlagStatus(AT24Cxx_I2C, I2C_ISR_TXIS) == RESET){if((AT24Cxx_Timeout--) == 0) {return AT24Cxx_TIMEOUT_UserCallback();}}#if defined(AT24C04) || defined(AT24C08)|| defined(AT24C16) || defined(AT24C32)|| defined(AT24C64) /* Send MSB of memory address */I2C_SendData(AT24Cxx_I2C, (uint8_t)((ReadAddr & 0xFF00) >> 8));/* Wait until TXIS flag is set */AT24Cxx_Timeout = AT24Cxx_LONG_TIMEOUT; while(I2C_GetFlagStatus(AT24Cxx_I2C, I2C_ISR_TXIS) == RESET){if((AT24Cxx_Timeout--) == 0)return AT24Cxx_TIMEOUT_UserCallback();}
#endif/* Send LSB of memory address */I2C_SendData(AT24Cxx_I2C, (uint8_t)(ReadAddr & 0x00FF));/* Wait until TC flag is set */AT24Cxx_Timeout = AT24Cxx_LONG_TIMEOUT;while(I2C_GetFlagStatus(AT24Cxx_I2C, I2C_ISR_TC) == RESET){if((AT24Cxx_Timeout--) == 0) return AT24Cxx_TIMEOUT_UserCallback();} /* If number of Reload cycles is not equal to 0 */if (Count != 0){/* Starting communication */StartCom = 1;/* Wait until all reload cycles are performed */while( Count != 0){ /* If a read transfer is performed */if (StartCom == 0) {/* Wait until TCR flag is set */AT24Cxx_Timeout = AT24Cxx_LONG_TIMEOUT; while(I2C_GetFlagStatus(AT24Cxx_I2C, I2C_ISR_TCR) == RESET){if((AT24Cxx_Timeout--) == 0) return AT24Cxx_TIMEOUT_UserCallback();}} /* if remains one read cycle */if ((Count == 1) && (NumbOfSingle == 0)){/* if starting communication */if (StartCom != 0){/* Configure slave address, end mode and start condition */I2C_TransferHandling(AT24Cxx_I2C, AT24Cxx_Address, 255, I2C_AutoEnd_Mode, I2C_Generate_Start_Read);}else{/* Configure slave address, end mode */I2C_TransferHandling(AT24Cxx_I2C, AT24Cxx_Address, 255, I2C_AutoEnd_Mode, I2C_No_StartStop); }}else {/* if starting communication */if (StartCom != 0){/* Configure slave address, end mode and start condition */I2C_TransferHandling(AT24Cxx_I2C, AT24Cxx_Address, 255, I2C_Reload_Mode, I2C_Generate_Start_Read);}else{/* Configure slave address, end mode */I2C_TransferHandling(AT24Cxx_I2C, AT24Cxx_Address, 255, I2C_Reload_Mode, I2C_No_StartStop); } }/* Update local variable */StartCom = 0; DataNum = 0;/* Wait until all data are received */while (DataNum != 255){ /* Wait until RXNE flag is set */AT24Cxx_Timeout = AT24Cxx_LONG_TIMEOUT;while(I2C_GetFlagStatus(AT24Cxx_I2C, I2C_ISR_RXNE) == RESET){if((AT24Cxx_Timeout--) == 0) return AT24Cxx_TIMEOUT_UserCallback();}/* Read data from RXDR */pBuffer[DataNum]= I2C_ReceiveData(AT24Cxx_I2C);/* Update number of received data */DataNum++;(*NumByteToRead)--;} /* Update Pointer of received buffer */ pBuffer += DataNum; /* update number of reload cycle */Count--;}/* If number of single data is not equal to 0 */if (NumbOfSingle != 0){ /* Wait until TCR flag is set */AT24Cxx_Timeout = AT24Cxx_LONG_TIMEOUT; while(I2C_GetFlagStatus(AT24Cxx_I2C, I2C_ISR_TCR) == RESET){if((AT24Cxx_Timeout--) == 0) return AT24Cxx_TIMEOUT_UserCallback();}/* Update CR2 : set Nbytes and end mode */I2C_TransferHandling(AT24Cxx_I2C, AT24Cxx_Address, (uint8_t)(NumbOfSingle), I2C_AutoEnd_Mode, I2C_No_StartStop);/* Reset local variable */DataNum = 0;/* Wait until all data are received */while (DataNum != NumbOfSingle){ /* Wait until RXNE flag is set */AT24Cxx_Timeout = AT24Cxx_LONG_TIMEOUT;while(I2C_GetFlagStatus(AT24Cxx_I2C, I2C_ISR_RXNE) == RESET){if((AT24Cxx_Timeout--) == 0) return AT24Cxx_TIMEOUT_UserCallback();}/* Read data from RXDR */pBuffer[DataNum]= I2C_ReceiveData(AT24Cxx_I2C);/* Update number of received data */DataNum++;(*NumByteToRead)--;} }} else{/* Update CR2 : set Slave Address , set read request, generate Start and set end mode */I2C_TransferHandling(AT24Cxx_I2C, AT24Cxx_Address, (uint32_t)(NumbOfSingle), I2C_AutoEnd_Mode, I2C_Generate_Start_Read);/* Reset local variable */DataNum = 0;/* Wait until all data are received */while (DataNum != NumbOfSingle){/* Wait until RXNE flag is set */AT24Cxx_Timeout = AT24Cxx_LONG_TIMEOUT; while(I2C_GetFlagStatus(AT24Cxx_I2C, I2C_ISR_RXNE) == RESET){if((AT24Cxx_Timeout--) == 0) return AT24Cxx_TIMEOUT_UserCallback();}/* Read data from RXDR */pBuffer[DataNum]= I2C_ReceiveData(AT24Cxx_I2C);/* Update number of received data */DataNum++;(*NumByteToRead)--;} } /* Wait until STOPF flag is set */AT24Cxx_Timeout = AT24Cxx_LONG_TIMEOUT;while(I2C_GetFlagStatus(AT24Cxx_I2C, I2C_ISR_STOPF) == RESET){if((AT24Cxx_Timeout--) == 0) return AT24Cxx_TIMEOUT_UserCallback();}/* Clear STOPF flag */I2C_ClearFlag(AT24Cxx_I2C, I2C_ICR_STOPCF);/* If all operations OK, return sEE_OK (0) */return AT24Cxx_OK;
}/************************ (C) COPYRIGHT LKL0305 ****************END OF FILE****/
H文件代码:
/* Define to prevent recursive inclusion -------------------------------------*/
#ifndef __BS_I2C_H
#define __BS_I2C_H/* Includes ------------------------------------------------------------------*/
#include "stm32f0xx.h"#define AT24Cxx_FLAG_TIMEOUT ((uint32_t)0x2000)
#define AT24Cxx_LONG_TIMEOUT ((uint32_t)(10 * AT24Cxx_FLAG_TIMEOUT))#define AT24Cxx_MAX_TRIALS_NUMBER 300#define AT24Cxx_OK 0
#define AT24Cxx_FAIL 1
#define AT24Cxx_I2C I2C2//AT24C01 AT24C02 一页 8Byte
//AT24C04 AT24C08 AT24C16 一页 16Byte
//AT24C32 AT24C64 一页 32Byte
//-------注意!!!本代码只适用24C64及以下的EEPROM ,大于8K的ROM不能使用此代码--------------
#define AT24C02 //定义你使用的芯片型号#if defined(AT24C01) || defined(AT24C02)#define AT24Cxx_PAGESIZE 8
#elif defined(AT24C04) || defined(AT24C08)|| defined(AT24C16) #define AT24Cxx_PAGESIZE 16
#else#define AT24Cxx_PAGESIZE 32
#endif#define AT24Cxx_HW_Address 0xAE//0xA0 这个注意对应你的硬件地址!!!!extern void AT24CXX_Init(void);
extern void AT24Cxx_WriteBuffer(uint8_t* pBuffer, uint16_t WriteAddr, uint16_t NumByteToWrite);
extern uint32_t AT24Cxx_ReadBuffer(uint8_t* pBuffer, uint16_t ReadAddr, uint16_t* NumByteToRead);#endif
主程序代码:
#include "stm32f0xx.h"
#include "bs_iic.h"int main(void)
{//app_run();//-----------IIC2-测试代码-----uint8_t read_b[64]={0};uint8_t wirte_b[64]={1,2,3,4,4,4,8,5,22,66,88,77};AT24CXX_Init();while(1){uint16_t r_num=10;uint16_t w_num=10;AT24Cxx_ReadBuffer(read_b,0,&r_num);//注意!这里num在读取数据后减少对应长度AT24Cxx_WriteBuffer(wirte_b,0,w_num);if(wirte_b[0]<250)wirte_b[0]++;elsewirte_b[0]=0;}}
STM32F030 IIC2通用读写24C02、24C16、24C32、24C64等例程相关推荐
- fm24c16c语言程序,单片机读写24C01~24C16程序
单片机读写24C01~24C16程序,24C02 read / write process 关键字:单片机读写24C01~24C16程序 单片机读写24C01~24C16程序 AT89S52 晶振频率 ...
- STM32CubeMX(5)——IIC读写24c02
0.序 我用的一个PCA9536老是出问题,怀疑是IIC应答或者停止位出问题了,所以特地来仔细看看IIC的原理和操作. (已经排除软件问题,是硬件电路问题) 本文使用软件模拟IIC,没有使用硬件自带I ...
- 16F877A和24C02通信汇编语言,PIC16f877A读写24c02程序
PIC16f877A读写24c02程序 来源:-- 作者:-- 浏览:389 时间:2016-08-10 14:18 标签: 摘要: PIC16f877A读写24c02程序 #include #in ...
- 单片机flash通用读写库:TZFlash
单片机flash通用读写库:TZFlash 本文博客链接:http://blog.csdn.net/jdh99,作者:jdh,转载请注明. 说明 本文发布单片机flash通用读写库TZFlash,有两 ...
- spi flash通用读写软IP
spi flash通用读写模块,有两个模块,分别为spiflash控制模块和spi控制模块 spiflash控制模块RTL代码如下: //功能描述 //这是一个spiflash的控制程序 //写选择( ...
- 24C16 与24C64系列 存储器的区别
在偶然一次情况下发现24C16的程序无法读写24C64,经过观察发现24C64的读写时序与24C16存在区别.区别在于24C16发送的地址是一个8位的,然后24C64需要的地址是一个16位的,发现这个 ...
- 【STM32CubeMX学习】I2C读写24C02
目录 1.I2C总线 2.I2C驱动编写 3.24C02 4.EEPROM读写函数编写 5.验证 1.I2C总线 I2C总线有两根线:时钟线SCL.数据线SDA,当总线空闲时,两根线都处于高电平. I ...
- 24c02 汇编语言,单片机读写24C02的汇编程序
;简洁的24C02读写汇编程序 ;-------------------------------------------- I2C_SDA EQU P1.6 ; PIN 5 I2 ...
- STM32读写24C02遇到的问题
这几天在弄I2C,读取24C02的数据.我默默的敲完了代码,然后仿真. 代码就下面两行,就是写一个字节,然后读取. I2C_EE_BufferWrite( &write,100, 1); I2 ...
最新文章
- UVA 11235 Frequent values(RMQ)
- linux man命令_CentOS Linux中的man命令
- python实现多语言语种识别_用Python进行语言检测
- findler mac 隐藏文件_fiddler使用实例之----------查找隐藏的真实地址!!!!
- 用Prim和Kruskal两种算法,求解最小生成树
- 一行Python代码统计词频
- linux系统下部署go语言环境
- [原创] Wireshark工具培训
- Highcharts使用=====通过指定日期显示曲线
- snoopy php https_php使用snoopy与curl模拟登陆的实例分享
- httpclient4.X 设置代理请求(包含账号密码)
- 6.无线射频基础知识介绍_无线射频工作原理
- windows embed sapi php,19.1 嵌入式SAPI
- 八键电话号码的字母组合
- 【Angular4】constructor ngOnInit
- php中Sessionopen,php使用session提示[function.session-start]: open解决方法
- 2021年上海第一批高新技术企业上海熙有网络科技集团榜上有名
- 函数极限的24种定义
- 利用U盘PE系统修复win7系统的启动引导文件
- echarts绘制3D地图
热门文章
- G1D17-研究方向rce45-49不快乐就去敲敲代码
- Memory Analyzer Tool 1 Shallow heap Retained heap dominator tree(控制树)
- SISR深度学习主要方法简述
- WIFI AP和STATION
- 小区宽带不能上网的解决办法
- linux内核网络TIME_WAIT
- Android Studio使用技巧系列教程(二)
- [C++11 多线程同步] --- 线程同步概述
- datastage 如何把db2的varchar列数据抽取到mysql的longtext列
- 第五章 全连接神经网络