Оформлены комментарии в I2C
This commit is contained in:
parent
400caa0aa5
commit
7e38106ce2
@ -5,7 +5,7 @@
|
||||
<provider copy-of="extension" id="org.eclipse.cdt.ui.UserLanguageSettingsProvider"/>
|
||||
<provider-reference id="org.eclipse.cdt.core.ReferencedProjectsLanguageSettingsProvider" ref="shared-provider"/>
|
||||
<provider-reference id="org.eclipse.cdt.managedbuilder.core.MBSLanguageSettingsProvider" ref="shared-provider"/>
|
||||
<provider class="org.eclipse.cdt.managedbuilder.language.settings.providers.GCCBuiltinSpecsDetector" console="false" env-hash="520753781973748679" id="ilg.gnuarmeclipse.managedbuild.cross.GCCBuiltinSpecsDetector" keep-relative-paths="false" name="CDT ARM Cross GCC Built-in Compiler Settings " parameter="${COMMAND} ${FLAGS} ${cross_toolchain_flags} -E -P -v -dD "${INPUTS}"" prefer-non-shared="true">
|
||||
<provider class="org.eclipse.cdt.managedbuilder.language.settings.providers.GCCBuiltinSpecsDetector" console="false" env-hash="-411648972679954456" id="ilg.gnuarmeclipse.managedbuild.cross.GCCBuiltinSpecsDetector" keep-relative-paths="false" name="CDT ARM Cross GCC Built-in Compiler Settings " parameter="${COMMAND} ${FLAGS} ${cross_toolchain_flags} -E -P -v -dD "${INPUTS}"" prefer-non-shared="true">
|
||||
<language-scope id="org.eclipse.cdt.core.gcc"/>
|
||||
<language-scope id="org.eclipse.cdt.core.g++"/>
|
||||
</provider>
|
||||
@ -16,7 +16,7 @@
|
||||
<provider copy-of="extension" id="org.eclipse.cdt.ui.UserLanguageSettingsProvider"/>
|
||||
<provider-reference id="org.eclipse.cdt.core.ReferencedProjectsLanguageSettingsProvider" ref="shared-provider"/>
|
||||
<provider-reference id="org.eclipse.cdt.managedbuilder.core.MBSLanguageSettingsProvider" ref="shared-provider"/>
|
||||
<provider class="org.eclipse.cdt.managedbuilder.language.settings.providers.GCCBuiltinSpecsDetector" console="false" env-hash="480357847621646132" id="ilg.gnuarmeclipse.managedbuild.cross.GCCBuiltinSpecsDetector" keep-relative-paths="false" name="CDT ARM Cross GCC Built-in Compiler Settings " parameter="${COMMAND} ${FLAGS} ${cross_toolchain_flags} -E -P -v -dD "${INPUTS}"" prefer-non-shared="true">
|
||||
<provider class="org.eclipse.cdt.managedbuilder.language.settings.providers.GCCBuiltinSpecsDetector" console="false" env-hash="-311328360447573477" id="ilg.gnuarmeclipse.managedbuild.cross.GCCBuiltinSpecsDetector" keep-relative-paths="false" name="CDT ARM Cross GCC Built-in Compiler Settings " parameter="${COMMAND} ${FLAGS} ${cross_toolchain_flags} -E -P -v -dD "${INPUTS}"" prefer-non-shared="true">
|
||||
<language-scope id="org.eclipse.cdt.core.gcc"/>
|
||||
<language-scope id="org.eclipse.cdt.core.g++"/>
|
||||
</provider>
|
||||
|
@ -1,14 +1,31 @@
|
||||
/*
|
||||
* V_i2cMem.h
|
||||
*
|
||||
* Created on: 15 àâã. 2019 ã.
|
||||
* Author: Dmitry
|
||||
*/
|
||||
/*!
|
||||
Copyright 2019 ÀÎ "ÍÈÈÝÒ" è ÎÎÎ "ÍÏÔ ÂÅÊÒÎÐ"
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
You may obtain a copy of the License at
|
||||
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
Unless required by applicable law or agreed to in writing, software
|
||||
distributed under the License is distributed on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
See the License for the specific language governing permissions and
|
||||
limitations under the License.
|
||||
|
||||
\file v_i2cMem.h
|
||||
\brief Äðàéâåð äëÿ ðàáîòû ñ ìèêðîñõåìîé ôëåø ïàìÿòè 24LC256 ïî
|
||||
èíòåðôåéñó I2C
|
||||
\author ÎÎÎ "ÍÏÔ Âåêòîð". http://motorcontrol.ru
|
||||
\version v 1.0 10/08/2019
|
||||
|
||||
\addtogroup v_i2cMem
|
||||
@{
|
||||
*/
|
||||
#ifndef INCLUDE_V_I2CMEM_H_
|
||||
#define INCLUDE_V_I2CMEM_H_
|
||||
|
||||
#define EEPROM_MEM_LENGTH 32768 //äëèíà ôëåøêè â áàéòàõ (256 êáèò)
|
||||
#define EEPROM_MEM_LENGTH 32768 // Ðàçìåð ïàìÿòè â áàéòàõ (256 êáèò)
|
||||
|
||||
struct SI2cMem;
|
||||
typedef volatile struct SI2cMem TI2cMem;
|
||||
@ -16,7 +33,7 @@ typedef volatile struct SI2cMem TI2cMem;
|
||||
struct SI2cMem {
|
||||
Uint16 MEMstartaddr; //! Àäðåñ íà flash
|
||||
Uint16 data_length; //! Äëèíà äàííûõ â áàéòàõ
|
||||
Uint16 *DSPstartaddr; //! Àäðåñ íà ìàññèâ ñ äàííûìè
|
||||
Uint16 *DSPstartaddr; //! Àäðåñ íà ìàññèâ ñ äàííûìè â êîíòðîëëåðå
|
||||
Uint16 LastErr; //! Êîä îøèáêè (åñëè âîçíèêëà)
|
||||
void (*init)(TI2cMem*);
|
||||
void (*write)(TI2cMem*);
|
||||
|
180
Vsrc/V_i2cMem.c
180
Vsrc/V_i2cMem.c
@ -1,10 +1,27 @@
|
||||
/*
|
||||
* V_i2cMem.c
|
||||
*
|
||||
* Created on: 15 àâã. 2019 ã.
|
||||
* Author: Dmitry
|
||||
*/
|
||||
/*!
|
||||
Copyright 2019 АО "НИИЭТ" и ООО "НПФ ВЕКТОР"
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
You may obtain a copy of the License at
|
||||
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
Unless required by applicable law or agreed to in writing, software
|
||||
distributed under the License is distributed on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
See the License for the specific language governing permissions and
|
||||
limitations under the License.
|
||||
|
||||
\file v_i2cMem.c
|
||||
\brief Драйвер для работы с микросхемой флеш памяти 24LC256 по
|
||||
интерфейсу I2C
|
||||
\author ООО "НПФ Вектор". http://motorcontrol.ru
|
||||
\version v 1.0 10/08/2019
|
||||
|
||||
\addtogroup v_i2cMem
|
||||
@{
|
||||
*/
|
||||
|
||||
#include "main.h"
|
||||
#include "V_i2cmem.h"
|
||||
@ -15,11 +32,17 @@
|
||||
|
||||
TI2cMem i2cMem = I2CMEM_DEFAULTS;
|
||||
|
||||
// Ôóíêöèÿ îæèäàíèÿ âûïîëíåíèÿ êîìàíäû
|
||||
// Желаемая частота шины I2C в килогерцах
|
||||
#define I2CMEM_FREQUENCY_KHZ 400
|
||||
|
||||
// Функция ожидания выполнения команды модулем I2C
|
||||
// Просто ждёт, пока модуль выйдет из состояния "IDLE"
|
||||
Uint16 i2c_waitIdle() {
|
||||
Uint32 idle = 0;
|
||||
|
||||
while ((I2C->ST & I2C_ST_MODE_Msk) == I2C_ST_MODE_IDLE){
|
||||
idle++;
|
||||
// Если ожидание слишком долгое - выдать ошибку
|
||||
if (idle > 10000000)
|
||||
return 1;
|
||||
};
|
||||
@ -27,7 +50,9 @@ Uint16 i2c_waitIdle() {
|
||||
return 0;
|
||||
}
|
||||
|
||||
// Ôóíêöèÿ æä¸ò, ïîêà çàêîí÷èòñÿ âíóòðåííèé öèêë çàïèñè â ïàìÿòè
|
||||
|
||||
// Функция ждёт, пока закончится внутренний цикл записи в микросхеме памяти.
|
||||
// Пока цикл идёт, микросхема не квитирует отправленный ей байт с собственным адресом и командой "Write"
|
||||
// Åñëè äîëæàëèñü, ïîêà ìèêðîñõåìà îñâîáîäèòñÿ, òî íà âûõîäå èç ôóíêöèè îíà áóäåò â ñîñòîÿíèè
|
||||
// îæèäàíèÿ ïðè¸ìà âíóòðåííåãî àäðåñà (òî åñòü å¸ ïîñëàí ñòàðò è àäðåñ óñòðîéñòâà ñ áèòîì "Write")
|
||||
Uint16 i2c_waitMemBusyAndSendAddWr () {
|
||||
@ -66,11 +91,13 @@ Uint16 i2c_waitMemBusyAndSendAddWr () {
|
||||
}
|
||||
} while ((I2C->ST & I2C_ST_MODE_Msk) != I2C_ST_MODE_MTADPA);
|
||||
|
||||
// Дошли до сюда - всё хорошо
|
||||
return I2C_MEM_ERROR_OK;
|
||||
}
|
||||
|
||||
|
||||
// Èíèò/ïåðåèíèò çàïèñè ìàññèâà, êîòîðûé íàäî âûçûâàòü ïðè äîñòèæåíèè ãðàíèöû ñòðàíèöû (64 áàéòà)
|
||||
// Вспомогательная функция для блочной записи данных в памяти.
|
||||
// Осуществляет инит/переинит записи массива, который надо вызывать
|
||||
// при достижении границы страницы (64 байта) внутри памяти.
|
||||
Uint16 i2c_initWriteArray (Uint16 address) {
|
||||
Uint16 retVal;
|
||||
// Æä¸ì, ïîêà ïàìÿòü ïàìÿòü çàêîí÷èí âíóòðåííåå ñîõðàíåíèå
|
||||
@ -100,16 +127,16 @@ Uint16 i2c_initWriteArray (Uint16 address) {
|
||||
return I2C_MEM_ERROR_OK;
|
||||
}
|
||||
|
||||
// Çàïèñü ìàññèâà
|
||||
// Запись массива байт в память.
|
||||
Uint16 i2c_writeArray(Uint16 address, Uint16 *dataPtr_u16, Uint16 length_u8) {
|
||||
// Òóò âíóòðè ïðîùå ðàáîòàòü ñ áàéòàìè
|
||||
Uint8* dataPtr_u8 = (Uint8*)dataPtr_u16;
|
||||
|
||||
// Отправляем адрес, с котрого начнём запись
|
||||
i2c_initWriteArray(address);
|
||||
|
||||
// Ïîåõàëè äàííûå
|
||||
// Отправляем данные
|
||||
while (length_u8 > 0) {
|
||||
// Äàííûå
|
||||
I2C->SDA = *dataPtr_u8;
|
||||
I2C->CTL0 = I2C_CTL0_CLRST_Msk;
|
||||
if (i2c_waitIdle() != 0) return I2C_MEM_ERROR_TIMEOUT;
|
||||
@ -118,11 +145,12 @@ Uint16 i2c_writeArray(Uint16 address, Uint16 *dataPtr_u16, Uint16 length_u8) {
|
||||
if ((I2C->ST & I2C_ST_MODE_Msk) != I2C_ST_MODE_MTDAPA)
|
||||
return I2C_MEM_ERROR_WRITE_HW_ERR;
|
||||
|
||||
// Ñìîòðèì, íå äîøëè ëè äî êîíöà ñòðàíèöû âíóòðè ïàìÿòè/
|
||||
// Åñëè äîøëè - íàäî ñäåëàòü ñòîï è ïîäîæäàòü, ïîêà äàííûå ïðîïèøóòñÿ
|
||||
length_u8--;
|
||||
dataPtr_u8++;
|
||||
address++;
|
||||
|
||||
// Смотрим, не дошли ли до конца страницы внутри памяти/
|
||||
// Если дошли - надо отправить стоп и подождать, пока данные пропишутся
|
||||
if ((address & 0x3F) == 0) {
|
||||
// Ôîðìèðóåì ñòîï è ïåðåçàïóñêàåì çàïèñûâàëêó íà íîâûé àäðåñ
|
||||
I2C->CTL0 = I2C_CTL0_STOP_Msk;
|
||||
@ -144,7 +172,7 @@ Uint16 i2c_readArray(Uint16 address, Uint16* readDataPtr_u16, Uint16 length_u8){
|
||||
|
||||
Uint16 retVal;
|
||||
|
||||
// Æä¸ì, ïîêà ïàìÿòü ïàìÿòü çàêîí÷èí âíóòðåííåå ñîõðàíåíèå
|
||||
// Ждём, пока память память закончит внутреннее сохранение
|
||||
retVal = i2c_waitMemBusyAndSendAddWr();
|
||||
if (retVal != I2C_MEM_ERROR_OK)
|
||||
return retVal;
|
||||
@ -185,8 +213,8 @@ Uint16 i2c_readArray(Uint16 address, Uint16* readDataPtr_u16, Uint16 length_u8){
|
||||
if ((I2C->ST & I2C_ST_MODE_Msk) != I2C_ST_MODE_MRADPA)
|
||||
return I2C_MEM_ERROR_READ_HW_ERR;
|
||||
|
||||
// До последнего байта принимаем и квитируем
|
||||
while (length_u8 > 1) {
|
||||
// Ïðèíèìàåì áàéò, è êâèòèðóåì
|
||||
I2C->CTL0 = I2C_CTL0_CLRST_Msk;
|
||||
if (i2c_waitIdle() != 0) return I2C_MEM_ERROR_TIMEOUT;
|
||||
|
||||
@ -216,9 +244,8 @@ Uint16 i2c_readArray(Uint16 address, Uint16* readDataPtr_u16, Uint16 length_u8){
|
||||
}
|
||||
|
||||
|
||||
// Æåëàåìàÿ ÷àñòîòà øèíû I2C â êèëîãåðöàõ
|
||||
#define I2CMEM_FREQUENCY_KHZ 400
|
||||
|
||||
// Инит модуля I2C и GPIO, к которым подключена память
|
||||
void I2CMEM_Init(TI2cMem*p){
|
||||
// Ðàçðåøàåì ðàáîòó 0 è 1 íîæåê ïîðòà À è ïåðåâîäèì èõ â ïåðèôåðèéíûé ðåæèì
|
||||
GPIOA->DENSET |= 0x3;
|
||||
@ -230,23 +257,25 @@ void I2CMEM_Init(TI2cMem*p){
|
||||
I2C->CTL1 |= (25000 / I2CMEM_FREQUENCY_KHZ) << I2C_CTL1_SCLFRQ_Pos;
|
||||
}
|
||||
|
||||
// Запись массива байтов
|
||||
void I2CMEM_Write(TI2cMem*p){
|
||||
// Çàïèñü
|
||||
p->LastErr = i2c_writeArray(p->MEMstartaddr, p->DSPstartaddr, p->data_length);
|
||||
}
|
||||
|
||||
// Чтение массива байтов
|
||||
void I2CMEM_Read(TI2cMem*p){
|
||||
// ×òåíèå
|
||||
p->LastErr = i2c_readArray(p->MEMstartaddr, p->DSPstartaddr, p->data_length);
|
||||
}
|
||||
|
||||
// Полная очистка памяти
|
||||
void I2CMEM_Clear(TI2cMem*p){
|
||||
// Ñòèðàíèå
|
||||
Uint32 i = 0;
|
||||
Uint16 ffArr[32];
|
||||
for (i = 0; i < 32; i++) {
|
||||
ffArr[i] = 0xFFFF;
|
||||
}
|
||||
|
||||
// Забиваем каждую страницу 0xFF
|
||||
for (i = 0; i < EEPROM_MEM_LENGTH; i += 0x40){
|
||||
p->MEMstartaddr = i;
|
||||
p->DSPstartaddr = ffArr;
|
||||
@ -257,109 +286,4 @@ void I2CMEM_Clear(TI2cMem*p){
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
/****** Äåïðåêåéòåä, êàê ãîâîðèòñÿ *******/
|
||||
//// Çàïèñü â ïàìÿòü îäíîãî áàéòà è "ñòîï"
|
||||
//Uint16 i2c_writeSingleByteAndStop(Uint16 address, Uint8 data)
|
||||
//{
|
||||
// Uint16 retVal;
|
||||
// // Æä¸ì, ïîêà ïàìÿòü ïàìÿòü çàêîí÷èí âíóòðåííåå ñîõðàíåíèå
|
||||
// retVal = i2c_waitMemBusyAndSendAddWr();
|
||||
// if (retVal != I2C_MEM_ERROR_OK)
|
||||
// return retVal;
|
||||
//
|
||||
// // Ñòðàøèé áàéò àäðåñà 0x0000____
|
||||
// I2C->SDA = (address >> 8) & 0xFF;
|
||||
// I2C->CTL0 = I2C_CTL0_CLRST_Msk;
|
||||
// if (i2c_waitIdle() != 0) return I2C_MEM_ERROR_TIMEOUT;
|
||||
//
|
||||
// // Åñëè íå êâèòèðîâàí - îøèáêà
|
||||
// if ((I2C->ST & I2C_ST_MODE_Msk) != I2C_ST_MODE_MTDAPA)
|
||||
// return I2C_MEM_ERROR_WRITE_HW_ERR;
|
||||
//
|
||||
// // Ìëàäøèé áàéò àäðåñà 0x____0000
|
||||
// I2C->SDA = (address >> 0) & 0xFF;
|
||||
// I2C->CTL0 = I2C_CTL0_CLRST_Msk;
|
||||
// if (i2c_waitIdle() != 0) return I2C_MEM_ERROR_TIMEOUT;
|
||||
//
|
||||
// // Åñëè íå êâèòèðîâàí - îøèáêà
|
||||
// if ((I2C->ST & I2C_ST_MODE_Msk) != I2C_ST_MODE_MTDAPA)
|
||||
// return I2C_MEM_ERROR_WRITE_HW_ERR;
|
||||
//
|
||||
// // Äàííûå
|
||||
// I2C->SDA = data;
|
||||
// I2C->CTL0 = I2C_CTL0_CLRST_Msk;
|
||||
// if (i2c_waitIdle() != 0) return I2C_MEM_ERROR_TIMEOUT;
|
||||
//
|
||||
// // Åñëè íå êâèòèðîâàí - îøèáêà
|
||||
// if ((I2C->ST & I2C_ST_MODE_Msk) != I2C_ST_MODE_MTDAPA)
|
||||
// return I2C_MEM_ERROR_WRITE_HW_ERR;
|
||||
//
|
||||
// // Ôîðìèðóåì ñòîï
|
||||
// I2C->CTL0 = I2C_CTL0_STOP_Msk;
|
||||
// I2C->CTL0 |= I2C_CTL0_CLRST_Msk;
|
||||
// return I2C_MEM_ERROR_OK;
|
||||
//}
|
||||
//
|
||||
//
|
||||
//// ×òåíèå îäíîãî áàéòà è ñòîï
|
||||
//Uint8 i2c_readSingleByteAndStop(Uint16 address, Uint16* readData)
|
||||
//{
|
||||
// Uint16 retVal;
|
||||
//
|
||||
// // Æä¸ì, ïîêà ïàìÿòü ïàìÿòü çàêîí÷èí âíóòðåííåå ñîõðàíåíèå
|
||||
// retVal = i2c_waitMemBusyAndSendAddWr();
|
||||
// if (retVal != I2C_MEM_ERROR_OK)
|
||||
// return retVal;
|
||||
//
|
||||
// // Ñòðàøèé áàéò àäðåñà 0x0000____
|
||||
// I2C->SDA = (address >> 8) & 0xFF;
|
||||
// I2C->CTL0 = I2C_CTL0_CLRST_Msk;
|
||||
// if (i2c_waitIdle() != 0) return I2C_MEM_ERROR_TIMEOUT;
|
||||
//
|
||||
// // Åñëè íå êâèòèðîâàí - îøèáêà
|
||||
// if ((I2C->ST & I2C_ST_MODE_Msk) != I2C_ST_MODE_MTDAPA)
|
||||
// return I2C_MEM_ERROR_READ_HW_ERR;
|
||||
//
|
||||
// // Ìëàäøèé áàéò àäðåñà 0x____0000
|
||||
// I2C->SDA = (address >> 0) & 0xFF;
|
||||
// I2C->CTL0 = I2C_CTL0_CLRST_Msk;
|
||||
// if (i2c_waitIdle() != 0) return I2C_MEM_ERROR_TIMEOUT;
|
||||
//
|
||||
// // Åñëè íå êâèòèðîâàí - îøèáêà
|
||||
// if ((I2C->ST & I2C_ST_MODE_Msk) != I2C_ST_MODE_MTDAPA)
|
||||
// return I2C_MEM_ERROR_READ_HW_ERR;
|
||||
//
|
||||
// // Ïîâòîðíûé ñòàðò, ÷òîáû ïåðåéòè â ðåæèì ìàñòåðà-ïðè¸ìíèêà
|
||||
// I2C->CTL0 = I2C_CTL0_START_Msk;
|
||||
// I2C->CTL0 |= I2C_CTL0_CLRST_Msk;
|
||||
// if (i2c_waitIdle() != 0) return I2C_MEM_ERROR_TIMEOUT;
|
||||
//
|
||||
// // Åñëè ðåæèì íåïðàâèëüíûé - îøèáêà
|
||||
// if ((I2C->ST & I2C_ST_MODE_Msk) != I2C_ST_MODE_RSDONE)
|
||||
// return I2C_MEM_ERROR_READ_HW_ERR;
|
||||
//
|
||||
// // Àäðåñ óñòðîéñòâà + Read
|
||||
// I2C->SDA = 0b10100001;
|
||||
// I2C->CTL0 = I2C_CTL0_CLRST_Msk;
|
||||
// if (i2c_waitIdle() != 0) return I2C_MEM_ERROR_TIMEOUT;
|
||||
//
|
||||
// // Åñëè ïåðåäà÷à àäðåñà óñòðîéñòâà íå êâèòèðîâàíà - îøèáêà
|
||||
// if ((I2C->ST & I2C_ST_MODE_Msk) != I2C_ST_MODE_MRADPA)
|
||||
// return I2C_MEM_ERROR_READ_HW_ERR;
|
||||
//
|
||||
// // Ïðèíèìàåì áàéò, íî íå êâèòèðóåì
|
||||
// I2C->CTL0 = I2C_CTL0_ACK_Msk; // Reset + NACK
|
||||
// I2C->CTL0 |= I2C_CTL0_CLRST_Msk;
|
||||
// if (i2c_waitIdle() != 0) return I2C_MEM_ERROR_TIMEOUT;
|
||||
//
|
||||
// // Åñëè ðåæèì íå ñòàë ïðàâèëüíûì - îøèáêà
|
||||
// if ((I2C->ST & I2C_ST_MODE_Msk) != I2C_ST_MODE_MRDANA)
|
||||
// return I2C_MEM_ERROR_READ_HW_ERR;
|
||||
//
|
||||
// *readData = I2C->SDA;
|
||||
// // Ôîðìèðóåì ñòîï
|
||||
// I2C->CTL0 = I2C_CTL0_STOP_Msk | I2C_CTL0_CLRST_Msk;
|
||||
//
|
||||
// return I2C_MEM_ERROR_OK;
|
||||
//}
|
||||
/*@}*/
|
||||
|
Loading…
Reference in New Issue
Block a user