Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: frequency measurements #126

Draft
wants to merge 1 commit into
base: main
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 5 additions & 5 deletions src/commands.c
Original file line number Diff line number Diff line change
Expand Up @@ -228,13 +228,13 @@ command_func_t* const cmd_table[NUM_PRIMARY_CMDS + 1][NUM_SECONDARY_CMDS_MAX + 1
},
{ // 10 TIMING
// 0 1 GET_TIMING 2 3
Undefined, Unimplemented, Undefined, Undefined,
Undefined, INTERVAL_UntilEvent, Undefined, Undefined,
// 4 START_ONE_CHAN_LA 5 START_TWO_CHAN_LA 6 START_FOUR_CHAN_LA 7 FETCH_DMA_DATA
LOGICANALYZER_OneChannel, LOGICANALYZER_TwoChannel, LOGICANALYZER_FourChannel, Removed,
// 8 FETCH_INT_DMA_DATA 9 FETCH_LONG_DMA_DATA 10 COMPARATOR_TO_LA 11 GET_INITIAL_STATES
BUFFER_FetchInt, BUFFER_FetchLong, Unimplemented, INTERVAL_GetState,
// 12 TIMING_MEASUREMENTS 13 INTERVAL_MEASUREMENTS 14 CONFIGURE_COMPARATOR 15 START_ALTERNATE_ONE_CHAN_LA
Unimplemented, Unimplemented, Removed, LOGICANALYZER_OneChannelAlt,
INTERVAL_TimeMeasure, INTERVAL_IntervalMeasure, Removed, LOGICANALYZER_OneChannelAlt,
// 16 START_THREE_CHAN_LA 17 STOP_LA 18 19
LOGICANALYZER_ThreeChannel, LOGICANALYZER_Stop, Undefined, Undefined,
// 20 21 22 23
Expand All @@ -244,17 +244,17 @@ command_func_t* const cmd_table[NUM_PRIMARY_CMDS + 1][NUM_SECONDARY_CMDS_MAX + 1
},
{ // 11 COMMON
// 0 1 GET_CTMU_VOLTAGE 2 GET_CAPACITANCE 3 GET_FREQUENCY
Undefined, MULTIMETER_GetCTMUVolts, MULTIMETER_GetCapacitance, Unimplemented,
Undefined, MULTIMETER_GetCTMUVolts, MULTIMETER_GetCapacitance, MULTIMETER_LowFrequency,
// 4 GET_INDUCTANCE 5 GET_VERSION 6 7
Unimplemented, DEVICE_GetVersion, Undefined, Undefined,
// 8 RETRIEVE_BUFFER 9 GET_HIGH_FREQUENCY 10 CLEAR_BUFFER 11 SET_RGB1
BUFFER_Retrieve, Unimplemented, BUFFER_Clear, Removed,
BUFFER_Retrieve, MULTIMETER_HighFrequency, BUFFER_Clear, Removed,
// 12 READ_PROGRAM_ADDRESS 13 WRITE_PROGRAM_ADDRESS 14 READ_DATA_ADDRESS 15 WRITE_DATA_ADDRESS
Removed, Removed, DEVICE_ReadRegisterData, DEVICE_WriteRegisterData,
// 16 GET_CAP_RANGE 17 SET_RGB2 18 READ_LOG 19 RESTORE_STANDALONE
MULTIMETER_GetCapRange, Removed, Removed, DEVICE_Reset,
// 20 GET_ALTERNATE_HIGH_FREQUENCY 21 SET_RGB_COMMON 22 SET_RGB3 23 START_CTMU
Unimplemented, LIGHT_RGBPin, Removed, CTMU_Start,
MULTIMETER_HighFrequencyAlt, LIGHT_RGBPin, Removed, CTMU_Start,
// 24 STOP_CTMU 25 START_COUNTING 26 FETCH_COUNT 27 FILL_BUFFER
CTMU_Stop, SENSORS_StartCounter, SENSORS_GetCounter, BUFFER_Fill,
},
Expand Down
109 changes: 109 additions & 0 deletions src/helpers/interval.c
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
#include "../registers/memory/dma.h"
#include "../registers/system/interrupt_manager.h"
#include "../registers/system/pin_manager.h"
#include "../registers/system/watchdog.h"
#include "../registers/timers/tmr2.h"
#include "buffer.h"

Expand Down Expand Up @@ -196,3 +197,111 @@ response_t INTERVAL_GetState(void) {

return SUCCESS;
}

response_t INTERVAL_IntervalMeasure(void) {

uint16_t timeout = UART1_ReadInt(); // t * 64e6 >> 16
uint8_t pins = UART1_Read();
uint8_t modes = UART1_Read();

IC_PARAMS_ConfigureIntervalCaptureWithIC1AndIC2(pins & 0xF,
IC_PARAMS_CAPTURE_TIMER_PERIPHERAL,
IC_PARAMS_CAPTURE_INTERRUPT_EVERY_EVENT, modes & 0x7);
IC_PARAMS_ConfigureIntervalCaptureWithIC3AndIC4((pins >> 4) & 0xF,
IC_PARAMS_CAPTURE_TIMER_PERIPHERAL,
IC_PARAMS_CAPTURE_INTERRUPT_EVERY_EVENT, (modes >> 3) & 0x7);

IC_PARAMS_ManualTriggerAll();

while ((!_IC1IF) && (IC2TMR < timeout)) WATCHDOG_TimerClear();
UART1_WriteInt(IC1BUF);
UART1_WriteInt(IC2BUF);

while ((!_IC3IF) && (IC2TMR < timeout)) WATCHDOG_TimerClear();
UART1_WriteInt(IC3BUF);
UART1_WriteInt(IC4BUF);
UART1_WriteInt(IC2TMR);

IC_PARAMS_DisableAllModules();

return SUCCESS;
}

response_t INTERVAL_TimeMeasure(void) {

uint16_t timeout = UART1_ReadInt(); // t * 64e6 >> 16
uint8_t pins = UART1_Read();
uint8_t modes = UART1_Read();
uint8_t intrpts = UART1_Read();

if ((pins & 0xF) == 4 || ((pins >> 4) & 0xF) == 4) {
CMP4_SetupComparator();
CVR_SetupComparator();
}

IC_PARAMS_ConfigureIntervalCaptureWithIC1AndIC2(pins & 0xF,
IC_PARAMS_CAPTURE_TIMER2, (intrpts & 0xF) - 1, modes & 0x7);
IC_PARAMS_ConfigureIntervalCaptureWithIC3AndIC4((pins >> 4) & 0xF,
IC_PARAMS_CAPTURE_TIMER2, ((intrpts >> 4) & 0xF) - 1, (modes >> 3) & 0x7);

TMR2_Initialize();

SetDefaultDIGITAL_STATES();

IC_PARAMS_ManualTriggerAll();
TMR2_Start();

if ((modes >> 6) & 0x1) {
RPOR5bits.RP54R = RPN_DEFAULT_PORT; // Disconnect SQR1 pin
((modes >> 7) & 0x1) ? SQR1_SetHigh() : SQR1_SetLow();
}

while ((!_IC1IF || !_IC3IF) && (IC2TMR < timeout)) WATCHDOG_TimerClear();

uint8_t i;
for (i = 0; i < (intrpts & 0xF); i++) {
UART1_WriteInt(IC1BUF);
UART1_WriteInt(IC2BUF);
}
for (i = 0; i < ((intrpts >> 4) & 0xF); i++) {
UART1_WriteInt(IC3BUF);
UART1_WriteInt(IC4BUF);
}

IC1_InterruptFlagClear();
IC3_InterruptFlagClear();

UART1_WriteInt(IC2TMR);

IC_PARAMS_DisableAllModules();
TMR2_Stop();

return SUCCESS;
}

response_t INTERVAL_UntilEvent(void) {

uint16_t timeout = UART1_ReadInt(); // t * 64e6 >> 16
uint8_t mode = UART1_Read();
uint8_t pin = UART1_Read();

IC_PARAMS_ConfigureIntervalCaptureWithIC1AndIC2(pin & 0xF,
IC_PARAMS_CAPTURE_TIMER_PERIPHERAL, (mode & 0x3) - 1, mode & 0x7);

while (!_IC1IF && (IC2TMR < timeout)) WATCHDOG_TimerClear();

IC1_InterruptFlagClear();

UART1_WriteInt(IC2TMR);

uint8_t i;
for (i = 0; i < (mode & 0x3); i++) {
UART1_WriteInt(IC1BUF);
UART1_WriteInt(IC2BUF);
}

IC_PARAMS_DisableAllModules();
TMR2_Stop();

return SUCCESS;
}
120 changes: 119 additions & 1 deletion src/helpers/interval.h
Original file line number Diff line number Diff line change
Expand Up @@ -86,8 +86,126 @@ extern "C" {
* @return None
*/
void INTERVAL_CaptureFour(uint16_t count, uint16_t mode, uint8_t prescaler);


/**
* @brief Reads DMA status registry data
*
* @description
* This method will sequentially read register addresses at BUFFER pointer
* and all four DMA channel pointers. It will also read digital state parameters.
*
* There are no input parameters to this method. The output of this method should
* be read over serial in the following order.
* 1. (int) BUFFER pointer
* 2. (int) DMA Channel 0 pointer
* 3. (int) DMA Channel 1 pointer
* 4. (int) DMA Channel 2 pointer
* 5. (int) DMA Channel 3 pointer
* 6. (char) Digital states
* 7. (char) Digital states error
*
* @return SUCCESS
*/
response_t INTERVAL_GetState(void);

/**
* @brief Measures the time interval between two pin state change events
*
* @description
* This method will count the time difference between two pin change events
* attached to two pins.
* The events can be any event defined at the list of events in `IC_PARAMS_CAPTURE_MODE`.
* The pins should be any pin in the list of `PIN_MANAGER_DIGITAL_PINS`.
*
* @param timeout : period of wait until the operation is aborted
* @param pins : input pins defined at `PIN_MANAGER_DIGITAL_PINS`
* | 7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 |
* | PIN EVENT 2 | PIN EVENT 1 |
* @param modes : pin change event defined at `IC_PARAMS_CAPTURE_MODE`
* | 7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 |
* | X | X | EVENT 2 | EVENT 1 |
*
* The output of this method should be read over serial in the following order.
* 1. (int) IC1BUF - LSW
* 2. (int) IC2BUF - MSW
* Combine 1. and 2. to get the trigger time of the event 1
* 3. (int) IC3BUF - LSW
* 4. (int) IC4BUF - MSW
* Combine 3. and 4. to get the trigger time of the event 2
* 5. (int) IC2TMR
*
* @return SUCCESS
*/
response_t INTERVAL_IntervalMeasure(void);

/**
* @brief Measures the time between multiple pin state change events
*
* @description
* This method will log time units for multiple changes occurred on
* defined digital pins. Unlike `INTERVAL_IntervalMeasure` where it
* measure only a single change of states, this method will measure
* upto 4 change of pin states.
* The events can be any event defined at the list of events in `IC_PARAMS_CAPTURE_MODE`.
* The pins should be any pin in the list of `PIN_MANAGER_DIGITAL_PINS`.
*
* @param timeout : period of wait until the operation is aborted
* @param pins : input pins defined at `PIN_MANAGER_DIGITAL_PINS`
* | 7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 |
* | PIN EVENT 2 | PIN EVENT 1 |
* @param modes : pin change event defined at `IC_PARAMS_CAPTURE_MODE`
* | 7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 |
* | X | X | EVENT 2 | EVENT 1 |
* @param intrpts : input pins defined at `PIN_MANAGER_DIGITAL_PINS`
* | 7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 |
* | INTERRUPT 2 | INTERRUPT 1 |
*
* The output of this method should be read over serial in the following order.
* 1. (int) IC1BUF - LSW
* 2. (int) IC2BUF - MSW
* Combine 1. and 2. to get the trigger time of the change event. Depending on the
* intrpts, the two registers (1. and 2.) may need to be read repeatedly to capture
* timing data for each event occurrence.
* 3. (int) IC3BUF - LSW
* 4. (int) IC4BUF - MSW
* Combine 3. and 4. to get the trigger time of the change event. Depending on the
* intrpts, the two registers (3. and 4.) may need to be read repeatedly to capture
* timing data for each event occurrence.
* Note: ICxBUF is a 4-level buffer that can store time log for four change events.
* 5. (int) IC2TMR
*
* @return SUCCESS
*/
response_t INTERVAL_TimeMeasure(void);

/**
* @brief Measures the time until a pin state change event occurs
*
* @description
* This method will stop counting time when the defined pin change event occurred.
* The event can be any event defined at the list of events in `IC_PARAMS_CAPTURE_MODE`.
* The pin should be any pin in the list of `PIN_MANAGER_DIGITAL_PINS`.
*
* @param timeout : period of wait until the operation is aborted
* @param mode : pin change event defined at `IC_PARAMS_CAPTURE_MODE`
* | 7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 |
* | X | X | X | X | X | EVENT |
* @param pin : input pin defined at `PIN_MANAGER_DIGITAL_PINS`
* | 7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 |
* | X | X | X | X | PIN EVENT |
*
* The output of this method should be read over serial in the following order.
* 1. (int) IC2TMR
* 2. (int) IC1BUF - LSW
* 3. (int) IC2BUF - MSW
* Combine 2. and 3. to get the trigger time of the change event. Depending on the mode,
* the last two registers (2. and 3.) may need to be read repeatedly to capture timing
* data for each event occurrence.
* Note: ICxBUF is a 4-level buffer that can store time log for four change events.
*
* @return SUCCESS
*/
response_t INTERVAL_UntilEvent(void);

// Getters and setters

Expand Down
Loading