📄 hal_adc.s51
字号:
ASEGN SFR_AN:DATA:NOROOT,0baH
// unsigned char volatile __sfr ADCL
ADCL:
DS 1
ASEGN SFR_AN:DATA:NOROOT,0bbH
// unsigned char volatile __sfr ADCH
ADCH:
DS 1
ASEGN SFR_AN:DATA:NOROOT,0f2H
// unsigned char volatile __sfr ADCCFG
ADCCFG:
DS 1
// 21 #include "hal_defs.h"
// 22 #include "hal_types.h"
// 23 #include "hal_adc.h"
// 24
// 25 /**************************************************************************************************
// 26 * CONSTANTS
// 27 **************************************************************************************************/
// 28 #define HAL_ADC_EOC 0x80 /* End of Conversion bit */
// 29 #define HAL_ADC_START 0x40 /* Starts Conversion */
// 30
// 31 #define HAL_ADC_STSEL_EXT 0x00 /* External Trigger */
// 32 #define HAL_ADC_STSEL_FULL 0x10 /* Full Speed, No Trigger */
// 33 #define HAL_ADC_STSEL_T1C0 0x20 /* Timer1, Channel 0 Compare Event Trigger */
// 34 #define HAL_ADC_STSEL_ST 0x30 /* ADCCON1.ST =1 Trigger */
// 35
// 36 #define HAL_ADC_RAND_NORM 0x00 /* Normal Operation */
// 37 #define HAL_ADC_RAND_LFSR 0x04 /* Clock LFSR */
// 38 #define HAL_ADC_RAND_SEED 0x08 /* Seed Modulator */
// 39 #define HAL_ADC_RAND_STOP 0x0c /* Stop Random Generator */
// 40 #define HAL_ADC_RAND_BITS 0x0c /* Bits [3:2] */
// 41
// 42 #define HAL_ADC_REF_125V 0x00 /* Internal 1.25V Reference */
// 43 #define HAL_ADC_REF_AIN7 0x40 /* AIN7 Reference */
// 44 #define HAL_ADC_REF_AVDD 0x80 /* AVDD_SOC Pin Reference */
// 45 #define HAL_ADC_REF_DIFF 0xc0 /* AIN7,AIN6 Differential Reference */
// 46 #define HAL_ADC_REF_BITS 0xc0 /* Bits [7:6] */
// 47
// 48 #define HAL_ADC_DEC_064 0x00 /* Decimate by 64 : 8-bit resolution */
// 49 #define HAL_ADC_DEC_128 0x10 /* Decimate by 128 : 10-bit resolution */
// 50 #define HAL_ADC_DEC_256 0x20 /* Decimate by 256 : 12-bit resolution */
// 51 #define HAL_ADC_DEC_512 0x30 /* Decimate by 512 : 14-bit resolution */
// 52 #define HAL_ADC_DEC_BITS 0x30 /* Bits [5:4] */
// 53
// 54 #define HAL_ADC_CHN_AIN0 0x00 /* AIN0 */
// 55 #define HAL_ADC_CHN_AIN1 0x01 /* AIN1 */
// 56 #define HAL_ADC_CHN_AIN2 0x02 /* AIN2 */
// 57 #define HAL_ADC_CHN_AIN3 0x03 /* AIN3 */
// 58 #define HAL_ADC_CHN_AIN4 0x04 /* AIN4 */
// 59 #define HAL_ADC_CHN_AIN5 0x05 /* AIN5 */
// 60 #define HAL_ADC_CHN_AIN6 0x06 /* AIN6 */
// 61 #define HAL_ADC_CHN_AIN7 0x07 /* AIN7 */
// 62 #define HAL_ADC_CHN_A0A1 0x08 /* AIN0,AIN1 */
// 63 #define HAL_ADC_CHN_A2A3 0x09 /* AIN2,AIN3 */
// 64 #define HAL_ADC_CHN_A4A5 0x0a /* AIN4,AIN5 */
// 65 #define HAL_ADC_CHN_A6A7 0x0b /* AIN6,AIN7 */
// 66 #define HAL_ADC_CHN_GND 0x0c /* GND */
// 67 #define HAL_ADC_CHN_VREF 0x0d /* Positive voltage reference */
// 68 #define HAL_ADC_CHN_TEMP 0x0e /* Temperature sensor */
// 69 #define HAL_ADC_CHN_VDD3 0x0f /* VDD/3 */
// 70 #define HAL_ADC_CHN_BITS 0x0f /* Bits [3:0] */
// 71
// 72 #define HAL_ADC_STSEL HAL_ADC_STSEL_ST
// 73 #define HAL_ADC_RAND_GEN HAL_ADC_RAND_STOP
// 74 #define HAL_ADC_REF_VOLT HAL_ADC_REF_AVDD
// 75 #define HAL_ADC_DEC_RATE HAL_ADC_DEC_064
// 76 #define HAL_ADC_SCHN HAL_ADC_CHN_VDD3
// 77 #define HAL_ADC_ECHN HAL_ADC_CHN_GND
// 78
// 79
// 80 /* Vdd limit values */
RSEG CODE_C:CODE:REORDER:NOROOT(0)
// 81 static __code const uint16 HalAdcVddLimit[] =
??HalAdcVddLimit:
DW 13980, 14854, 15728, 16601, 17475, 18349, 19223, 20097, 20970
// 82 {
// 83 0x369C, /* VDD Limit - 1.6v */
// 84 0x3A06, /* VDD Limit - 1.7v */
// 85 0x3D70, /* VDD Limit - 1.8v */
// 86 0x40D9, /* VDD Limit - 1.9v */
// 87 0x4443, /* VDD Limit - 2.0v */
// 88 0x47AD, /* VDD Limit - 2.1v */
// 89 0x4B17, /* VDD Limit - 2.2v */
// 90 0x4E81, /* VDD Limit - 2.3v */
// 91 0x51EA, /* VDD Limit - 2.4v */
// 92 };
// 93
// 94
// 95 /**************************************************************************************************
// 96 * MACROS
// 97 **************************************************************************************************/
// 98 #define HAL_ADC_CLR_EOC() asm("PUSH A"); asm("MOV A,ADCL"); asm("MOV A,ADCH"); asm("POP A");
// 99
// 100 /**************************************************************************************************
// 101 * TYPEDEFS
// 102 **************************************************************************************************/
// 103
// 104 /**************************************************************************************************
// 105 * GLOBAL VARIABLES
// 106 **************************************************************************************************/
// 107
// 108 /**************************************************************************************************
// 109 * FUNCTIONS - API
// 110 **************************************************************************************************/
// 111 extern bool HalAdcCheckVdd (uint8 limit);
// 112
// 113 /**************************************************************************************************
// 114 * @fn HalAdcInit
// 115 *
// 116 * @brief Initialize ADC Service
// 117 *
// 118 * @param None
// 119 *
// 120 * @return None
// 121 **************************************************************************************************/
RSEG BANKED_CODE:CODE:NOROOT(0)
// 122 void HalAdcInit (void)
HalAdcInit:
CFI Block cfiBlock0 Using cfiCommon0
CFI Function HalAdcInit
// 123 {
PUSH DPL
CFI DPL0 Frame(CFA_SP, 4)
CFI CFA_SP SP+-4
PUSH DPH
CFI DPH0 Frame(CFA_SP, 5)
CFI CFA_SP SP+-5
; Saved register size: 2
; Auto size: 1
MOV A,#-0x1
LCALL ?ALLOC_XSTACK8
CFI CFA_XSP16 add(XSP16, 1)
// 124 #if (HAL_ADC == TRUE)
// 125 volatile uint8 tmp;
// 126
// 127 ADCCON1 = HAL_ADC_STSEL | HAL_ADC_RAND_GEN | 0x03;
MOV 0xb4,#0x3f
// 128 ADCCON2 = HAL_ADC_REF_VOLT | HAL_ADC_DEC_RATE | HAL_ADC_SCHN;
MOV 0xb5,#-0x71
// 129 /*
// 130 * After reset, the first ADC reading of the extra conversion always reads GND level.
// 131 * We will do a few dummy conversions to bypass this bug.
// 132 */
// 133 tmp = ADCL; /* read ADCL,ADCH to clear EOC */
MOV A,0xba
MOV DPL,?XSP + 0
MOV DPH,?XSP + 1
MOVX @DPTR,A
// 134 tmp = ADCH;
MOV A,0xbb
MOVX @DPTR,A
// 135 ADCCON3 = HAL_ADC_REF_VOLT | HAL_ADC_DEC_RATE | HAL_ADC_ECHN;
MOV 0xb6,#-0x74
// 136 while ((ADCCON1 & HAL_ADC_EOC) != HAL_ADC_EOC); /* Wait for conversion */
??HalAdcInit_0:
MOV A,0xb4
MOV C,0xE0 /* A */.7
JNC ??HalAdcInit_0
// 137 tmp = ADCL; /* read ADCL,ADCH to clear EOC */
MOV A,0xba
MOVX @DPTR,A
// 138 tmp = ADCH;
MOV A,0xbb
MOVX @DPTR,A
// 139 ADCCON3 = HAL_ADC_REF_VOLT | HAL_ADC_DEC_RATE | HAL_ADC_ECHN;
MOV 0xb6,#-0x74
// 140 while ((ADCCON1 & HAL_ADC_EOC) != HAL_ADC_EOC); /* Wait for conversion */
??HalAdcInit_1:
MOV A,0xb4
MOV C,0xE0 /* A */.7
JNC ??HalAdcInit_1
// 141 tmp = ADCL; /* read ADCL,ADCH to clear EOC */
MOV A,0xba
MOVX @DPTR,A
// 142 tmp = ADCH;
MOV A,0xbb
MOVX @DPTR,A
// 143 #endif
// 144 }
MOV A,#0x1
LCALL ?DEALLOC_XSTACK8
CFI EndBlock cfiBlock0
REQUIRE ?Subroutine0
; // Fall through to label ?Subroutine0
RSEG BANKED_CODE:CODE:NOROOT(0)
?Subroutine0:
CFI Block cfiBlock1 Using cfiCommon0
CFI NoFunction
CFI CFA_SP SP+-5
CFI DPL0 Frame(CFA_SP, 4)
CFI DPH0 Frame(CFA_SP, 5)
POP DPH
CFI CFA_SP SP+-4
CFI DPH0 SameValue
POP DPL
CFI CFA_SP SP+-3
CFI DPL0 SameValue
LJMP ?BRET
CFI EndBlock cfiBlock1
// 145
// 146 /**************************************************************************************************
// 147 * @fn HalAdcRead
// 148 *
// 149 * @brief Read the ADC based on given channel and resolution
// 150 *
// 151 * @param channel - channel where ADC will be read
// 152 * @param resolution - the resolution of the value
// 153 *
// 154 * @return 16 bit value of the ADC in offset binary format.
// 155 * Note that the ADC is "bipolar", which means the GND (0V) level is mid-scale.
// 156 **************************************************************************************************/
RSEG BANKED_CODE:CODE:NOROOT(0)
// 157 uint16 HalAdcRead (uint8 channel, uint8 resolution)
HalAdcRead:
CFI Block cfiBlock2 Using cfiCommon0
CFI Function HalAdcRead
// 158 {
MOV A,#-0xa
LCALL ?BANKED_ENTER_XDATA
CFI DPH0 load(1, XDATA, add(CFA_XSP16, literal(-1)))
CFI DPL0 load(1, XDATA, add(CFA_XSP16, literal(-2)))
CFI ?BRET_EXT load(1, XDATA, add(CFA_XSP16, literal(-3)))
CFI ?RET_HIGH load(1, XDATA, add(CFA_XSP16, literal(-4)))
CFI ?RET_LOW load(1, XDATA, add(CFA_XSP16, literal(-5)))
CFI R7 load(1, XDATA, add(CFA_XSP16, literal(-6)))
CFI V1 load(1, XDATA, add(CFA_XSP16, literal(-7)))
CFI V0 load(1, XDATA, add(CFA_XSP16, literal(-8)))
CFI VB load(1, XDATA, add(CFA_XSP16, literal(-9)))
CFI R6 load(1, XDATA, add(CFA_XSP16, literal(-10)))
CFI CFA_SP SP+0
CFI CFA_XSP16 add(XSP16, 10)
; Saved register size: 10
; Auto size: 1
MOV A,#-0x1
LCALL ?ALLOC_XSTACK8
CFI CFA_XSP16 add(XSP16, 11)
// 159 int16 reading = 0;
// 160
// 161 #if (HAL_ADC == TRUE)
// 162
// 163 uint8 i, resbits;
// 164 uint8 adctemp;
// 165 volatile uint8 tmp;
// 166 uint8 adcChannel = 1;
MOV R4,#0x1
// 167
// 168 /*
// 169 * If Analog input channel is AIN0..AIN7, make sure corresponing P0 I/O pin is enabled. The code
// 170 * does NOT disable the pin at the end of this function. I think it is better to leave the pin
// 171 * enabled because the results will be more accurate. Because of the inherent capacitance on the
// 172 * pin, it takes time for the voltage on the pin to charge up to its steady-state level. If
// 173 * HalAdcRead() has to turn on the pin for every conversion, the results may show a lower voltage
// 174 * than actuality because the pin did not have time to fully charge.
// 175 */
// 176 if (channel < 8)
MOV A,R1
CLR C
SUBB A,#0x8
JNC ??HalAdcRead_0
// 177 {
// 178 for (i=0; i < channel; i++)
MOV R3,#0x0
SJMP ??HalAdcRead_1
// 179 {
// 180 adcChannel <<= 1;
??HalAdcRead_2:
MOV A,R4
CLR C
RLC A
MOV R4,A
// 181 }
INC R3
??HalAdcRead_1:
MOV A,R3
CLR C
SUBB A,R1
JC ??HalAdcRead_2
// 182 }
// 183
// 184 /* Enable channel */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -