John Garlitos / Mbed OS EVAL-CN0540-ARDZ

Dependencies:   platform_drivers LTC26X6 AD77681

main.cpp

Committer:
jngarlitos
Date:
2021-12-06
Revision:
1:9dd7c64b4a64
Parent:
0:b9debc14d077

File content as of revision 1:9dd7c64b4a64:

/******************************************************************************
 *Copyright (c)2020 Analog Devices, Inc.  
 *
 * Licensed under the 2020-04-27-CN0540EC License(the "License");
 * you may not use this file except in compliance with the License.
 *
 ****************************************************************************/
#include <mbed.h>
#include "platform_drivers.h"
#include <assert.h>
#include "main.h"
#include "cn0540_app_config.h"
#include "platform_drivers.h"
#include "cn0540_init_params.h"

extern "C"{
#include "ad77681.h"
#include "cn0540_adi_fft.h" 
#include "ltc26x6.h"
}
// Descriptor of the main device - the ADC AD7768-1
ad77681_dev *device_adc;
// Structure carying measured data, sampled by the ADC
adc_data measured_data;
// AD7768-1's status register structure, carying all the error flags
ad77681_status_registers *current_status;
// Initialize the interrupt event variable
volatile bool int_event= false;

// Descriptor of the DAC LTC2606
ltc26x6_dev *device_dac;

// Structure carying data, the FFT module works with                
fft_entry *FFT_data;    
// Structure carying measuremtns from the FFT module                                
fft_measurements *FFT_meas; 

// Initialize the serial object with TX and RX pins
Serial pc(USBTX, USBRX);

// Initialize the drdy pin as interrupt input
InterruptIn drdy(DRDY_PIN, PullNone);
// Initialize the adc_rst_pin pin as digital output
DigitalOut adc_reset(ADC_RST_PIN);
// Initialize the buffer enable control pin as digital output
DigitalOut buffer_en(ARD_BUF_EN_PIN);
// Initialize the red LED control pin as digital output
DigitalOut led_red(ARD_RED_LED_PIN);
// Initialize the blue LED pin as digital output
DigitalOut led_blue(ARD_BLUE_LED_PIN);

/**
 * ADC data recteption interrupt from DRDY
 * 
 * Data reception from the ADC using interrupt generated by the ADC's DRDY (Data Ready) pin
 * Interrupt triggers falling edge of the active-high DRDY pulse
 * DRDY pulse is generated by the ADC and frequency of the DRDY pulse depends on the ADC settings:
 * 
 * DRDY frequency = MCLK / ( MCLK_DIV * FILTER_OSR )
 */
void drdy_interrupt()
{
    int_event = true;

    if (measured_data.count == measured_data.samples) { // Desired numer of samples has been taken, set everything back
        drdy.disable_irq();                             // Disable interrupt on DRDY pin
        measured_data.finish = true;                    // Desired number of samples has been taken
        measured_data.count = 0;                        // Set measured data counter to 0
    }
}
/**
 *=================================================================================================================================
 *
 * //////////////////////////////////////////////////    MAIN function      \\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\
 *
 *==================================================================================================================================
 */
int main() {

    int32_t connected = FAILURE;
    uint32_t menu;

    sdpk1_gpio_setup();                                                     // Setup SDP-K1 GPIOs
    adc_hard_reset();                                                       // Perform ADC hard reset
    connected = ad77681_setup(&device_adc, init_params, &current_status);   // SETUP and check connection
    if(connected == FAILURE)
        go_to_error();      
    ltc26x6_init(&device_dac, init_params_dac);                             // Initialize DAC
    
    #ifdef CN0540_ADI_FFT_H_                                                // if the adi_fft.h is included , initialize it
    FFT_init_params(&FFT_data, &FFT_meas);                                  // Initialize FFT structure and allocate space
    update_FFT_enviroment(device_adc->vref, device_adc->mclk, device_adc->sample_rate, FFT_data);   // Update the Vref, Mclk, Sampling rate
    measured_data.samples = 4096;                                           // Initialize FFT with 4096 samples
    FFT_init(measured_data.samples, FFT_data);                              // Update sample count for FFT
    #endif // CN0540_ADI_FFT_H_                                                    // FFT module is initializedd with 4096 samples and 7-term BH window

    print_title();
    print_prompt();

//============ MAIN WHILE ====================//    
    while(1)
    {
        
        if (pc.readable()) { // Settings menu SWITCH
            getUserInput(&menu);
            
            switch (menu) {     
            case 1:
                menu_1_set_adc_powermode();     // Set ADC power mode
                break;
            case 2:
                menu_2_set_adc_clock_divider(); // Set ADC clock divider
                break;
            case 3:
                menu_3_set_adc_filter_type();   // Set ad7768-1 filter type
                break;
            case 4:
                menu_4_adc_buffers_controll();  // Set ADC AIN & Reference buffers
                break;
            case 5:
                menu_5_set_default_settings();  // Set ADC default value
                break;
            case 6:
                menu_6_set_adc_vcm();           // Set ADC VCM
                break;  
            case 7:
                menu_7_adc_read_register();     // Read ADC register
                break;
            case 8:
                menu_8_adc_cont_read_data();    // Perform continuous ADC read
                break;
            case 9:
                menu_9_reset_ADC();             // Reset ADC
                break;
            case 10:
                menu_10_power_down();           // ADC Wake up and sleep 
                break;
            case 11:
                menu_11_ADC_GPIO();             // Set ADC GPIOs
                break;
            case 12:
                menu_12_read_master_status();   // Read ADC master status
                break;
            case 13:
                menu_13_mclk_vref();            // Set ADC MCLK / Vref
                break;
            case 14:
                menu_14_print_measured_data();  // Print continouos ADC read data
                break;
            case 15:
                menu_15_set_adc_data_output_mode(); // Set ADC data output mode 
                break;
            case 16:
                menu_16_set_adc_diagnostic_mode();  // Set ADC to diagnostic mode
                break;
            case 17:
                menu_17_do_the_fft();               // Perform FFT
                break;
            case 18:
                menu_18_fft_settings();             // Change FFT settins
                break;
            case 19:
                menu_19_gains_offsets();            // Set ADC gain and offset
                break;
            case 20:
                menu_20_check_scratchpad();         // Perform scratchpad check
                break;
            case 21:
                menu_21_piezo_offset();             // Compensate piezo offset
                break;
            case 22:
                menu_22_set_DAC_output();           // Set DAC output mode
                break;
            default:
                pc.printf("Invalid option");
                print_prompt();
                break;
            }
        }
    }   
}

/**
 * Error warning, in case of unsuccessfull SPI connection
 *
 */
void static go_to_error()
{
    int32_t connected = FAILURE;
    uint8_t scratchpad_sequence = 0xAD;
    while (1) {
        pc.printf("ERROR: NOT CONNECTED\nCHECK YOUR PHYSICAL CONNECTION\n\n");  // When not connected, keep showing error message
        wait(5);
        connected = ad77681_setup(&device_adc, init_params, &current_status);   // Keep trying to connect
        if (connected == SUCCESS) {
            pc.printf("SUCCESSFULLY RECONNECTED\n\n");                          // If successfull reading from scratchpad, init the ADC and go back
            break;
        }
    }
}

/**
 * Print title
 *
 */
void static print_title() {
    pc.printf("\n\r");
    pc.printf("****************************************************************\n");
    pc.printf("*      EVAL-CN0540-PMDZ Demonstration Program -- (mbed)        *\n");
    pc.printf("*                                                              *\n");
    pc.printf("*   This program demonstrates IEPE / ICP piezo accelerometer   *\n");
    pc.printf("*        interfacing and FFT measurements using AD7768-1       *\n");
    pc.printf("*           Precision 24-bit sigma-delta AD converter          *\n");
    pc.printf("*                                                              *\n");
    pc.printf("* Set the baud rate to 115200 select the newline terminator.   *\n");
    pc.printf("****************************************************************\n");
}

/**
 * Print main menu to console
 *
 */
void static print_prompt() {
    pc.printf("\n\nCommand Summary:\n\n");
    pc.printf("  1  - Set ADC power mode\n");
    pc.printf("  2  - Set ADC MCLK divider\n");
    pc.printf("  3  - Set ADC filter type\n");
    pc.printf("  4  - Set ADC AIN and REF buffers\n");
    pc.printf("  5  - Set ADC to default config\n");
    pc.printf("  6  - Set ADC VCM output\n");
    pc.printf("  7  - Read desired ADC register\n");
    pc.printf("  8  - Read continuous ADC data\n");
    pc.printf("  9  - Reset ADC\n");
    pc.printf("  10 - ADC Power-down\n");
    pc.printf("  11 - Set ADC GPIOs\n");
    pc.printf("  12 - Read ADC master status\n");
    pc.printf("  13 - Set ADC Vref and MCLK\n");
    pc.printf("  14 - Print ADC measured data\n");
    pc.printf("  15 - Set ADC data output mode\n");
    pc.printf("  16 - Set ADC diagnostic mode\n");
    pc.printf("  17 - Do the FFT\n");
    pc.printf("  18 - FFT settings\n");
    pc.printf("  19 - Set ADC Gains, Offsets\n");
    pc.printf("  20 - ADC Scratchpad Check\n");
    pc.printf("  21 - Compenzate Piezo sensor offset\n");
    pc.printf("  22 - Set DAC output\n");
    pc.printf("\n\r");
}

/**
 * Read user input from uart
 * *UserInput = 0 if failure
 *
 */
int32_t static getUserInput(uint32_t *UserInput)
{
    long uart_val;
    int32_t ret;

    ret = pc.scanf("%ld", &uart_val);       // Return 1 = OK, Return 0 = Fail

    if((ret == 0) || (uart_val < 0)) {      // Failure if uart_val is negative, or non-digit
        *UserInput = 0;
        return FAILURE;
    }
    *UserInput = (uint32_t)(uart_val);
    return SUCCESS;
}

/**
 * Set power mode
 *
 */
 void static menu_1_set_adc_powermode(void)
 {  
    uint32_t new_pwr_mode;
    
    pc.printf(" Avaliable power modes: \n");
    pc.printf("  1 - Low power mode\n");
    pc.printf("  2 - Median power mode\n");
    pc.printf("  3 - Fast power mode\n");
    pc.printf(" Select an option: \n");

    getUserInput(&new_pwr_mode);    
    pc.putc('\n');
    
    switch (new_pwr_mode) { 
    case 1:
        ad77681_set_power_mode(device_adc, AD77681_ECO);
        pc.printf(" Low power mode selected\n");
        break;
    case 2:
        ad77681_set_power_mode(device_adc, AD77681_MEDIAN);
        pc.printf(" Median power mode selected\n");
        break;
    case 3:
        ad77681_set_power_mode(device_adc, AD77681_FAST);
        pc.printf(" Fast power mode selected\n");
        break;
    default:
        pc.printf(" Invalid option\n");
        break;
    }
    print_prompt();
}

/**
 * Set clock divider
 *
 */
 void static menu_2_set_adc_clock_divider(void)
 {
    uint32_t new_mclk_div;
    
    pc.printf(" Avaliable MCLK divide options: \n");
    pc.printf("  1 - MCLK/16\n");
    pc.printf("  2 - MCLK/8\n");
    pc.printf("  3 - MCLK/4\n");
    pc.printf("  4 - MCLK/2\n");
    pc.printf(" Select an option: \n");
        
    getUserInput(&new_mclk_div);    
    pc.putc('\n');
    
    switch (new_mclk_div) { 
    case 1:
        ad77681_set_mclk_div(device_adc, AD77681_MCLK_DIV_16);
        pc.printf(" MCLK/16 selected\n");
        break;
    case 2:
        ad77681_set_mclk_div(device_adc, AD77681_MCLK_DIV_8);
        pc.printf(" MCLK/8 selected\n");
        break;
    case 3:
        ad77681_set_mclk_div(device_adc, AD77681_MCLK_DIV_4);
        pc.printf(" MCLK/4 selected\n");
        break;
    case 4:
        ad77681_set_mclk_div(device_adc, AD77681_MCLK_DIV_2);
        pc.printf(" MCLK/2 selected\n");
        break;
    default:
        pc.printf(" Invalid option\n");
        break;
    }
    // Update the sample rate after changing the MCLK divider
    ad77681_update_sample_rate(device_adc);         
    print_prompt();
}

/**
 * Set filter type
 *
 */
 void static menu_3_set_adc_filter_type(void) 
{
    uint32_t new_filter = 0;
    int32_t ret;
    
    pc.printf(" Avaliable clock divide options: \n");
    pc.printf(" 1 - SINC3 Fileter\n");
    pc.printf(" 2 - SINC5 Filter\n");
    pc.printf(" 3 - Low ripple FIR Filter\n");
    pc.printf(" 4 - SINC3 50/60Hz rejection\n");
    pc.printf(" 5 - User-defined FIR filter\n");
    pc.printf(" Select an option: \n");
    
    getUserInput(&new_filter);  
    pc.putc('\n');
    
    switch (new_filter) {   
    case 1:
        set_adc_SINC3_filter();
        break;      
    case 2:
        set_adc_SINC5_filter();
        break;      
    case 3:
        set_adc_FIR_filter();
        break;  
    case 4:
        set_adc_50HZ_rej();
        break;  
    case 5:
        set_adc_user_defined_FIR();
        break;      
    default:
        pc.printf(" Invalid option\n");
        break;
    }
    // Update the sample rate after changing the Filter type
    ad77681_update_sample_rate(device_adc); 
    print_prompt();
}

/**
 * Set SINC3 filter
 *
 */
void static set_adc_SINC3_filter(void)
{   
    uint32_t new_sinc3 = 0, new_sinc5 = 0;
    int32_t ret;
    
    pc.printf(" SINC3 filter Oversampling ratios: \n");
    pc.printf(" OSR is calculated as (x + 1)*32\n");
    pc.printf(" x is SINC3 OSR register value\n");
    pc.printf(" Please input a value from 0 to 8192 = 2^13\n  :");
        
    ret = getUserInput(&new_sinc3);

    if ((new_sinc3 >= 0) && (new_sinc3 <= 8192) && (ret == SUCCESS)) {
        pc.printf("%d\n", new_sinc3);
        ad77681_set_filter_type(device_adc, AD77681_SINC5_FIR_DECx32, AD77681_SINC3, new_sinc3);
        pc.printf(" SINC3 OSR is set to %d\n", (new_sinc3 + 1) * 32);
    } else {
        pc.printf("%d\n", new_sinc3);
        pc.printf(" Invalid option - too large number\n");
    }    
}

/**
 * Set SINC5 filter
 *
 */
void static set_adc_SINC5_filter(void)
{
    uint32_t new_sinc5;
    
    pc.printf(" SINC5 filter Oversampling ratios: \n");
    pc.printf("  1 - Oversampled by 8\n");
    pc.printf("  2 - Oversampled by 16\n");
    pc.printf("  3 - Oversampled by 32\n");
    pc.printf("  4 - Oversampled by 64\n");
    pc.printf("  5 - Oversampled by 128\n");
    pc.printf("  6 - Oversampled by 256\n");
    pc.printf("  7 - Oversampled by 512\n");
    pc.printf("  8 - Oversampled by 1024\n");
    pc.printf(" Select an option: \n");
        
    getUserInput(&new_sinc5);
        
    pc.putc('\n');
        
    switch (new_sinc5) {
    case 1:
        ad77681_set_filter_type(device_adc, AD77681_SINC5_FIR_DECx32, AD77681_SINC5_DECx8, 0);
        pc.printf(" SINC5 with OSRx8 set\n");
        break;
    case 2:
        ad77681_set_filter_type(device_adc, AD77681_SINC5_FIR_DECx32, AD77681_SINC5_DECx16, 0);
        pc.printf(" SINC5 with OSRx16 set\n");
        break;
    case 3:
        ad77681_set_filter_type(device_adc, AD77681_SINC5_FIR_DECx32, AD77681_SINC5, 0);
        pc.printf(" SINC5 with OSRx32 set\n");
        break;
    case 4:
        ad77681_set_filter_type(device_adc, AD77681_SINC5_FIR_DECx64, AD77681_SINC5, 0);
        pc.printf(" SINC5 with OSRx64 set\n");
        break;
    case 5:
        ad77681_set_filter_type(device_adc, AD77681_SINC5_FIR_DECx128, AD77681_SINC5, 0);
        pc.printf(" SINC5 with OSRx128 set\n");
        break;
    case 6:
        ad77681_set_filter_type(device_adc, AD77681_SINC5_FIR_DECx256, AD77681_SINC5, 0);
        pc.printf(" SINC5 with OSRx256 set\n");
        break;
    case 7:
        ad77681_set_filter_type(device_adc, AD77681_SINC5_FIR_DECx512, AD77681_SINC5, 0);
        pc.printf(" SINC5 with OSRx512 set\n");
        break;
    case 8:
        ad77681_set_filter_type(device_adc, AD77681_SINC5_FIR_DECx1024, AD77681_SINC5, 0);
        pc.printf(" SINC5 with OSRx1024 set\n");
        break;
    default:
        pc.printf(" Invalid option\n");
        break;
    }   
}

/**
 * Set FIR filter
 *
 */
void static set_adc_FIR_filter(void)
{
    uint32_t new_fir;
    
    pc.printf(" FIR filter Oversampling ratios: \n");
    pc.printf("  1 - Oversampled by 32\n");
    pc.printf("  2 - Oversampled by 64\n");
    pc.printf("  3 - Oversampled by 128\n");
    pc.printf("  4 - Oversampled by 256\n");
    pc.printf("  5 - Oversampled by 512\n");
    pc.printf("  6 - Oversampled by 1024\n");
    pc.printf(" Select an option: \n");
        
    getUserInput(&new_fir);
        
    pc.putc('\n');
        
    switch (new_fir) {
    case 1:
        ad77681_set_filter_type(device_adc, AD77681_SINC5_FIR_DECx32, AD77681_FIR, 0);
        pc.printf(" FIR with OSRx32 set\n");
        break;
    case 2:
        ad77681_set_filter_type(device_adc, AD77681_SINC5_FIR_DECx64, AD77681_FIR, 0);
        pc.printf(" FIR with OSRx64 set\n");
        break;
    case 3:
        ad77681_set_filter_type(device_adc, AD77681_SINC5_FIR_DECx128, AD77681_FIR, 0);
        pc.printf(" FIR with OSRx128 set\n");
        break;
    case 4:
        ad77681_set_filter_type(device_adc, AD77681_SINC5_FIR_DECx256, AD77681_FIR, 0);
        pc.printf(" FIR with OSRx256 set\n");
        break;
    case 5:
        ad77681_set_filter_type(device_adc, AD77681_SINC5_FIR_DECx512, AD77681_FIR, 0);
        pc.printf(" FIR with OSRx512 set\n");
        break;
    case 6:
        ad77681_set_filter_type(device_adc, AD77681_SINC5_FIR_DECx1024, AD77681_FIR, 0);
        pc.printf(" FIR with OSRx1024 set\n");
        break;
    default:
        pc.printf(" Invalid option\n");
        break;
    }           
}

/**
 * Set 50HZ rejection bit when SINC3 is being used
 *
 */
void static set_adc_50HZ_rej(void)
{
    uint32_t new_50Hz;
    
    pc.printf(" SINC3 50/60Hz rejection: \n");
    pc.printf("  1 - 50/60Hz rejection enable \n");
    pc.printf("  2 - 50/60Hz rejection disable \n");
    pc.printf(" Select an option: \n");
        
    getUserInput(&new_50Hz);
        
    pc.putc('\n');
        
    switch (new_50Hz)
    {
    case 1:
        ad77681_set_50HZ_rejection(device_adc, ENABLE);
        pc.printf(" SINC3 50/60Hz rejection enabled\n");
        break;
    case 2:
        ad77681_set_50HZ_rejection(device_adc, DISABLE);
        pc.printf(" SINC3 50/60Hz rejection disabled\n");
        break;
    default:
        pc.printf(" Invalid option\n");
        break;
    }   
}

/**
 * Insert user-defined FIR filter coeffs
 *
 */
void static set_adc_user_defined_FIR(void) 
{
    const uint8_t coeff_reg_length = 56; // Maximum allowed number of coefficients in the coeff register                                        

    pc.printf(" User Defined FIR filter\n");
    
    if ((ARRAY_SIZE(programmable_FIR) <= coeff_reg_length) && (count_of_active_coeffs <= coeff_reg_length)) {
        pc.printf("  Aplying user-defined FIR filter coefficients from 'FIR_user_coeffs.h'\n");
        ad77681_programmable_filter(device_adc, programmable_FIR, count_of_active_coeffs);
        pc.printf(" Coeffs inserted successfully\n");
    } else
        pc.printf("  Incorrect count of coefficients in 'FIR_user_coeffs.h'\n");    
}

/**
 * AIN and REF buffers controll
 *
 */
 void static menu_4_adc_buffers_controll(void)
 {
    uint32_t new_AIN_buffer = 0, new_REF_buffer = 0, new_buffer = 0;
    
    pc.printf(" Buffers settings: \n");
    pc.printf("  1 - Set AIN precharge buffers\n");
    pc.printf("  2 - Set REF buffers\n");
    pc.printf(" Select an option: \n");
        
    getUserInput(&new_buffer);
    pc.putc('\n');
    
    switch (new_buffer) {
    case 1:
        pc.printf(" Analog IN precharge buffers settings: \n");
        pc.printf("  1 - Turn ON  both precharge buffers\n");
        pc.printf("  2 - Turn OFF both precharge buffers\n");
        pc.printf("  3 - Turn ON  AIN- precharge buffer\n");
        pc.printf("  4 - Turn OFF AIN- precharge buffer\n");
        pc.printf("  5 - Turn ON  AIN+ precharge buffer\n");
        pc.printf("  6 - Turn OFF AIN+ precharge buffer\n");
        pc.printf(" Select an option: \n");
                
        getUserInput(&new_AIN_buffer);
        pc.putc('\n');
        
        switch (new_AIN_buffer) {
        case 1:
            ad77681_set_AINn_buffer(device_adc, AD77681_AINn_ENABLED);
            ad77681_set_AINp_buffer(device_adc, AD77681_AINp_ENABLED);
            pc.printf(" AIN+ and AIN- enabled\n");
            break;
        case 2:
            ad77681_set_AINn_buffer(device_adc, AD77681_AINn_DISABLED);
            ad77681_set_AINp_buffer(device_adc, AD77681_AINp_DISABLED);
            pc.printf(" AIN+ and AIN- disabled\n");
            break;
        case 3:
            ad77681_set_AINn_buffer(device_adc, AD77681_AINn_ENABLED);
            pc.printf(" AIN- Enabled\n");
            break;
        case 4:
            ad77681_set_AINn_buffer(device_adc, AD77681_AINn_DISABLED);
            pc.printf(" AIN- Disabled\n");
            break;
        case 5:
            ad77681_set_AINp_buffer(device_adc, AD77681_AINp_ENABLED);
            pc.printf(" AIN+ Enabled\n");
            break;
        case 6:
            ad77681_set_AINp_buffer(device_adc, AD77681_AINp_DISABLED);
            pc.printf(" AIN+ Disabled\n");
            break;
        default:
            pc.printf(" Invalid option\n");
            break;
        }       
        break;
    case 2:
        pc.printf(" REF buffers settings: \n");
        pc.printf("  1 - Full REF- reference buffer\n");
        pc.printf("  2 - Full REF+ reference buffer\n");
        pc.printf("  3 - Unbuffered REF- reference buffer\n");
        pc.printf("  4 - Unbuffered REF+ reference buffer\n");
        pc.printf("  5 - Precharge  REF- reference buffer\n");
        pc.printf("  6 - Precharge  REF+ reference buffer\n");
        pc.printf(" Select an option: \n");
        
        getUserInput(&new_REF_buffer);
        pc.putc('\n');
        
        switch (new_REF_buffer) {
        case 1:
            ad77681_set_REFn_buffer(device_adc, AD77681_BUFn_FULL_BUFFER_ON);
            pc.printf(" Fully buffered REF-\n");
            break;
        case 2:
            ad77681_set_REFp_buffer(device_adc, AD77681_BUFp_FULL_BUFFER_ON);
            pc.printf(" Fully buffered REF+\n");
            break;
        case 3:
            ad77681_set_REFn_buffer(device_adc, AD77681_BUFn_DISABLED);
            pc.printf(" Unbuffered REF-\n");
            break;
        case 4:
            ad77681_set_REFp_buffer(device_adc, AD77681_BUFp_DISABLED);
            pc.printf(" Unbuffered REF+\n");
            break;
        case 5:
            ad77681_set_REFn_buffer(device_adc, AD77681_BUFn_ENABLED);
            pc.printf(" Precharge buffer on REF-\n");
            break;
        case 6:
            ad77681_set_REFp_buffer(device_adc, AD77681_BUFp_ENABLED);
            pc.printf(" Precharge buffer on REF+\n");
            break;
        default:
            pc.printf(" Invalid option\n");
            break;
        }       
        break;      
    default:
        pc.printf(" Invalid option\n");
        break;
    }
    print_prompt();
}

/**
 * Default ADC Settings
 *
 */
 void static menu_5_set_default_settings(void)
 {  
    int32_t default_settings_flag  = ad77681_setup(&device_adc, init_params, &current_status);
    
    if (default_settings_flag == SUCCESS)
        pc.printf("\n Default ADC settings successfull\n");
    else
        pc.printf("\n Error in settings, please reset the ADC\n");
    print_prompt();
}

/**
 * VCM output controll
 *
 */
 void static menu_6_set_adc_vcm(void)
 {
    uint32_t new_vcm = 0;
    
    pc.printf(" Avaliable VCM output voltage levels: \n");
    pc.printf("  1 - VCM = (AVDD1-AVSS)/2\n");
    pc.printf("  2 - VCM = 2.5V\n");
    pc.printf("  3 - VCM = 2.05V\n");
    pc.printf("  4 - VCM = 1.9V\n");
    pc.printf("  5 - VCM = 1.65V\n");
    pc.printf("  6 - VCM = 1.1V\n");
    pc.printf("  7 - VCM = 0.9V\n");
    pc.printf("  8 - VCM off\n");
    pc.printf(" Select an option: \n");
    
    getUserInput(&new_vcm);
    pc.putc('\n');
    
    switch (new_vcm) {
    
    case 1:
        ad77681_set_VCM_output(device_adc, AD77681_VCM_HALF_VCC);
        pc.printf(" VCM set to half of the Vcc\n");
        break;
    case 2:
        ad77681_set_VCM_output(device_adc, AD77681_VCM_2_5V);
        pc.printf(" VCM set to 2.5V\n");
        break;
    case 3:
        ad77681_set_VCM_output(device_adc, AD77681_VCM_2_05V);
        pc.printf(" VCM set to 2.05V\n");
        break;
    case 4:
        ad77681_set_VCM_output(device_adc, AD77681_VCM_1_9V);
        pc.printf(" VCM set to 1.9V\n");
        break;
    case 5:
        ad77681_set_VCM_output(device_adc, AD77681_VCM_1_65V);
        pc.printf(" VCM set to 1.65V\n");
        break;
    case 6:
        ad77681_set_VCM_output(device_adc, AD77681_VCM_1_1V);
        pc.printf(" VCM set to 1.1V\n");
        break;
    case 7:
        ad77681_set_VCM_output(device_adc, AD77681_VCM_0_9V);
        pc.printf(" VCM set to 0.9V\n");
        break;      
    case 8:
        ad77681_set_VCM_output(device_adc, AD77681_VCM_OFF);
        pc.printf(" VCM OFF\n");
        break;
    default:
        pc.printf(" Invalid option\n");
        break;
    }
    print_prompt();
}

/**
 * Register read
 *
 */
 void static menu_7_adc_read_register(void)
 {
    uint32_t new_reg_to_read = 0;
    uint8_t reg_read_buf[3], read_adc_data[6], hex_number = 0;
    uint8_t HI = 0, MID = 0, LO = 0;
    char binary_number[8], other_register[2] = "";
    double voltage;
    
    pc.printf(" Read desired register: \n");
    pc.printf("  1 - 0x03        - Chip type\n");
    pc.printf("  2 - 0x14        - Interface format\n");
    pc.printf("  3 - 0x15        - Power clock\n");
    pc.printf("  4 - 0x16        - Analog\n");
    pc.printf("  5 - 0x17        - Analog2\n");
    pc.printf("  6 - 0x18        - Conversion\n");
    pc.printf("  7 - 0x19        - Digital filter\n");
    pc.printf("  8 - 0x1A        - SINC3 Dec. rate MSB\n");
    pc.printf("  9 - 0x1B        - SINC3 Dec. rate LSB\n");
    pc.printf(" 10 - 0x1C        - Duty cycle ratio\n");
    pc.printf(" 11 - 0x1D        - Sync, Reset\n");
    pc.printf(" 12 - 0x1E        - GPIO Controll\n");
    pc.printf(" 13 - 0x1F        - GPIO Write\n");
    pc.printf(" 14 - 0x20        - GPIO Read\n");
    pc.printf(" 15 - 0x21 - 0x23 - Offset register\n");
    pc.printf(" 16 - 0x24 - 0x26 - Gain register\n");
    pc.printf(" 17 - 0x2C        - ADC Data\n");
    pc.printf(" Select an option: \n");
    
    getUserInput(&new_reg_to_read);
    pc.putc('\n');
    
    switch (new_reg_to_read) {  
    case 1:
        ad77681_spi_reg_read(device_adc, AD77681_REG_CHIP_TYPE, reg_read_buf);
        print_binary(reg_read_buf[1], binary_number);
        pc.printf(" Value of 0x03 - Chip type register is: 0x%x  0b%s\n", reg_read_buf[1], binary_number);
        break;
    case 2:
        ad77681_spi_reg_read(device_adc, AD77681_REG_INTERFACE_FORMAT, reg_read_buf);
        print_binary(reg_read_buf[1], binary_number);
        pc.printf(" Value of 0x14 - Interface format register is: 0x%x  0b%s\n", reg_read_buf[1], binary_number);
        break;
    case 3:
        ad77681_spi_reg_read(device_adc, AD77681_REG_POWER_CLOCK, reg_read_buf);
        print_binary(reg_read_buf[1], binary_number);
        pc.printf(" Value of 0x15 - Power clock register is: 0x%x  0b%s\n", reg_read_buf[1], binary_number);
        break;
    case 4:
        ad77681_spi_reg_read(device_adc, AD77681_REG_ANALOG, reg_read_buf);
        print_binary(reg_read_buf[1], binary_number);
        pc.printf(" Value of 0x16 - Anlaog register is: 0x%x  0b%s\n", reg_read_buf[1], binary_number);
        break;
    case 5:
        ad77681_spi_reg_read(device_adc, AD77681_REG_ANALOG2, reg_read_buf);
        print_binary(reg_read_buf[1], binary_number);
        pc.printf(" Value of 0x17 - Analog2 regster is: 0x%x  0b%s\n", reg_read_buf[1], binary_number);
        break;
    case 6:
        ad77681_spi_reg_read(device_adc, AD77681_REG_CONVERSION, reg_read_buf);
        print_binary(reg_read_buf[1], binary_number);
        pc.printf(" Value of 0x18 - Conversion register is: 0x%x  0b%s\n", reg_read_buf[1], binary_number);
        break;
    case 7:
        ad77681_spi_reg_read(device_adc, AD77681_REG_DIGITAL_FILTER, reg_read_buf);
        print_binary(reg_read_buf[1], binary_number);
        pc.printf(" Value of 0x19 - Digital filter register is: 0x%x  0b%s\n", reg_read_buf[1], binary_number);
        break;
    case 8:
        ad77681_spi_reg_read(device_adc, AD77681_REG_SINC3_DEC_RATE_MSB, reg_read_buf);
        print_binary(reg_read_buf[1], binary_number);
        pc.printf(" Value of 0x1A - SINC3 Dec. rate MSB is: 0x%x  0b%s\n", reg_read_buf[1], binary_number);
        break;
    case 9:
        ad77681_spi_reg_read(device_adc, AD77681_REG_SINC3_DEC_RATE_LSB, reg_read_buf);
        print_binary(reg_read_buf[1], binary_number);
        pc.printf(" Value of 0x1B - SINC3 Dec. rate LSB is: 0x%x  0b%s\n", reg_read_buf[1], binary_number);
        break;
    case 10:
        ad77681_spi_reg_read(device_adc, AD77681_REG_DUTY_CYCLE_RATIO, reg_read_buf);
        print_binary(reg_read_buf[1], binary_number);
        pc.printf(" Value of 0x1C - Duty cycle ratio 0x%x  0b%s\n", reg_read_buf[1], binary_number);
        break;
    case 11:
        ad77681_spi_reg_read(device_adc, AD77681_REG_SYNC_RESET, reg_read_buf);
        print_binary(reg_read_buf[1], binary_number);
        pc.printf(" Value of 0x1D - Sync, Reset 0x%x  0b%s\n", reg_read_buf[1], binary_number);
        break;
    case 12:
        ad77681_spi_reg_read(device_adc, AD77681_REG_GPIO_CONTROL, reg_read_buf);
        print_binary(reg_read_buf[1], binary_number);
        pc.printf(" Value of 0x1E - GPIO Controll is: 0x%x  0b%s\n", reg_read_buf[1], binary_number);
        break;
    case 13:
        ad77681_spi_reg_read(device_adc, AD77681_REG_GPIO_WRITE, reg_read_buf);
        print_binary(reg_read_buf[1], binary_number);
        pc.printf(" Value of 0x1F - GPIO Write is: 0x%x  0b%s\n", reg_read_buf[1], binary_number);
        break;
    case 14:
        ad77681_spi_reg_read(device_adc, AD77681_REG_GPIO_READ, reg_read_buf);
        print_binary(reg_read_buf[1], binary_number);
        pc.printf(" Value of 0x20 - GPIO Read is: 0x%x  0b%s\n", reg_read_buf[1], binary_number);
        break;
    case 15:
        ad77681_spi_reg_read(device_adc, AD77681_REG_OFFSET_HI, reg_read_buf);
        HI = reg_read_buf[1];
        
        ad77681_spi_reg_read(device_adc, AD77681_REG_OFFSET_MID, reg_read_buf);
        MID = reg_read_buf[1];
        
        ad77681_spi_reg_read(device_adc, AD77681_REG_OFFSET_LO, reg_read_buf);
        LO = reg_read_buf[1];
        
        pc.printf(" Value of 0x21 - 0x23 - Offset register is: 0x%x %x %x\n", HI, MID, LO);
        break;
        
    case 16:
        ad77681_spi_reg_read(device_adc, AD77681_REG_GAIN_HI, reg_read_buf);
        HI = reg_read_buf[1];
        
        ad77681_spi_reg_read(device_adc, AD77681_REG_GAIN_MID, reg_read_buf);
        MID = reg_read_buf[1];
        
        ad77681_spi_reg_read(device_adc, AD77681_REG_GAIN_LO, reg_read_buf);
        LO = reg_read_buf[1];
        
        pc.printf(" Value of 0x24 - 0x26 - Gain register is: 0x%x %x %x\n", HI, MID, LO);
        break;  
    case 17:
        ad77681_spi_read_adc_data(device_adc, read_adc_data, AD77681_REGISTER_DATA_READ);
        pc.printf(" Value of 0x2C - ADC data is: 0x%x 0x%x 0x%x\n", read_adc_data[1], read_adc_data[2], read_adc_data[3]);
        break;  

    default :
        pc.printf(" Invalid option\n");
        break;
    }
    print_prompt();
}

/**
 * Read ADC data
 *
 */
void static menu_8_adc_cont_read_data(void)
{
    uint32_t new_sample_count = 0;
    int32_t ret;

    pc.printf(" Read Continuous ADC Data");
    pc.printf("  Input number of samples (1 to 4096): \n");
    ret = getUserInput(&new_sample_count);                  // Get user input

    if ((new_sample_count <= 4096) && (ret == SUCCESS) ) {
        pc.printf("\n%d of samples\n", new_sample_count);   // Print Desired Measurement Count
        measured_data.samples = (uint16_t)(new_sample_count);
        measured_data.finish = false;
        measured_data.count = 0;
        pc.printf("Sampling....\n");
        cont_sampling();
        pc.printf("Done Sampling....\n");
    } else {
        pc.printf(" Invalid option\n");
    }
    print_prompt();
}

/**
 * ADC Continuous read
 *
 */
void static cont_sampling()
{      
    uint8_t buf[6];
     
    ad77681_set_continuos_read(device_adc, AD77681_CONTINUOUS_READ_ENABLE);
    __enable_irq();                                             // Enable all interupts
    drdy.enable_irq();                                          // Enable interrupt on DRDY pin
    drdy.fall(&drdy_interrupt);                                 // Interrupt on falling edne of DRDY

    while (!measured_data.finish) { // While loop. Waiting for the measurements to be completed
        if (int_event==true) {      // Checks if Interrupt Occurred
            ad77681_spi_read_adc_data(device_adc, buf, AD77681_CONTINUOUS_DATA_READ);    // Read the continuous read data
            if (device_adc->conv_len == AD77681_CONV_24BIT)                                                 // 24bit format
                measured_data.raw_data[measured_data.count] = (buf[0] << 16 | buf[1] << 8 | buf[2]<< 0);    // Combining the SPI buffers
            else                                                                                            // 16bit format
                measured_data.raw_data[measured_data.count] = (buf[0] << 8 | buf[1]<< 0);                   // Combining the SPI buffers
            measured_data.count++;  // Increment Measured Data Counter
            int_event=false;        // Set int event flag after reading the Data
        }
    }
    ad77681_set_continuos_read(device_adc, AD77681_CONTINUOUS_READ_DISABLE);    // Disable continuous ADC read
}

/**
 * Reset ADC
 *
 */
 void static menu_9_reset_ADC(void)
 {
    uint32_t new_reset_option = 0;
    
    pc.printf(" ADC reset opportunities: \n");
    pc.printf("  1 - Soft reset - over SPI\n");
    pc.printf("  2 - Hard reset - uing RESET pin\n");
    pc.printf(" Select an option: \n");
        
    getUserInput(&new_reset_option);
    pc.putc('\n');
    
    switch (new_reset_option) {
    case 1:
        ad77681_soft_reset(device_adc);             // Perform soft reset thru SPI write
        pc.printf(" ADC after soft reset\n");
        break;
    case 2:
        adc_hard_reset();
        pc.printf(" ADC after hard reset\n");
        break;
    default:
        pc.printf(" Invalid option\n");
        break;
    }
    print_prompt();
}

/**
 * Reset ADC thru SDP-K1 GPIO
 * 
 * 
 */
 void static adc_hard_reset()
{
    adc_reset = 0;  // Set ADC reset pin to Low
    mdelay(100);    // Delay 100ms
    adc_reset = 1;  // Set ADC reset pin to High
    mdelay(100);    // Delay 100ms
}

/**
 * Sleep mode / Wake up ADC
 *
 */
 void static menu_10_power_down(void)
 {
    uint32_t new_sleep = 0;
    
    pc.printf(" Controll sleep mode of the ADC: \n");
    pc.printf("  1 - Put ADC to sleep mode\n");
    pc.printf("  2 - Wake up ADC\n");
    pc.printf(" Select an option: \n");
        
    getUserInput(&new_sleep);
    pc.putc('\n');
    
    switch (new_sleep) {
    case 1:
        ad77681_power_down(device_adc, AD77681_SLEEP);
        pc.printf(" ADC put to sleep mode\n");
        break;
    case 2:
        ad77681_power_down(device_adc, AD77681_WAKE);
        pc.printf(" ADC powered\n");
        break;
    default:
        pc.printf("Invalid option\n");
        break;          
    }
    print_prompt();
}

/**
 * ADC's GPIO Controll
 *
 */
 void static menu_11_ADC_GPIO(void) 
 {
    uint8_t GPIO_state;
    uint32_t new_gpio_sel = 0;
    char binary_number[8];
    int32_t ret_val = FAILURE, ret;
    
    pc.printf(" ADC GPIO Controll: \n");
    pc.printf("  1 - Read from GPIO\n");
    pc.printf("  2 - Write to  GPIO\n");
    pc.printf("  3 - Set GPIO as input / output\n");
    pc.printf("  4 - Change GPIO settings\n");
    pc.printf(" Select an option: \n");
    
    getUserInput(&new_gpio_sel);
    pc.putc('\n');
    
    switch (new_gpio_sel) {     
    case 1:
        ad77681_gpio_read(device_adc, &GPIO_state, AD77681_ALL_GPIOS);
        print_binary(GPIO_state, binary_number);
        pc.printf(" Current GPIO Values:\n GPIO0: %c\n GPIO1: %c\n GPIO2: %c\n GPIO3: %c\n", binary_number[7], binary_number[6], binary_number[5], binary_number[4]);
        break;      
    case 2:
        adc_GPIO_write();
        break;  
    case 3:
        adc_GPIO_inout();       
        break;          
    case 4:
        adc_GPIO_settings();        
        break;      
    default:
        pc.printf(" Invalid option\n");
        break;  
    }
    print_prompt();
}

/**
 * Write to GPIOs, part of the ADC_GPIO function
 *
 */
void static adc_GPIO_write(void)
{
    uint32_t new_gpio_write = 0, new_value = 0;
    int32_t ret, ret_val;
    
    pc.printf(" Write to GPIO: \n");
    pc.printf("  1 - Write to all GPIOs\n");
    pc.printf("  2 - Write to GPIO0\n");
    pc.printf("  3 - Write to GPIO1\n");
    pc.printf("  4 - Write to GPIO2\n");
    pc.printf("  5 - Write to GPIO3\n");
    pc.printf(" Select an option: \n");
        
    getUserInput(&new_gpio_write);      
    pc.putc('\n');
        
    switch (new_gpio_write)
    {
    case 1:
        pc.printf("Insert value to be writen into all GPIOs, same value for all GPIOs: ");
        ret = getUserInput(&new_value);
            
        if (((new_value == GPIO_HIGH) || (new_value == GPIO_LOW)) && (ret == SUCCESS)) {
            new_value *= 0xF;
            ret_val = ad77681_gpio_write(device_adc, new_value, AD77681_ALL_GPIOS);
            pc.printf("\n Value %d successully written to all GPOIs\n", new_value);
        } else
            pc.printf("\nInvalid value\n");             
        break;          
    case 2:
        pc.printf("Insert value to be written into GPIO0: ");
        ret = getUserInput(&new_value); 
            
        if (((new_value == GPIO_HIGH) || (new_value == GPIO_LOW)) && (ret == SUCCESS)) {
            ret_val = ad77681_gpio_write(device_adc, new_value, AD77681_GPIO0);
            pc.printf("\n Value %d successully written to GPIO0\n", new_value);
        } else
            pc.printf("\nInvalid value\n");         
        break;          
    case 3:
        pc.printf("Insert value to be written into GPIO1: ");
        ret = getUserInput(&new_value);         
            
        if (((new_value == GPIO_HIGH) || (new_value == GPIO_LOW)) && (ret == SUCCESS)) {
            ret_val = ad77681_gpio_write(device_adc, new_value, AD77681_GPIO1);
            pc.printf("\n Value %d successully written to GPIO1\n", new_value);
        } else
            pc.printf("\nInvalid value\n");         
        break;          
    case 4:
        pc.printf("Insert value to be written into GPIO2: ");
        ret = getUserInput(&new_value); 
            
        if (((new_value == GPIO_HIGH) || (new_value == GPIO_LOW)) && (ret == SUCCESS)) {
            ret_val = ad77681_gpio_write(device_adc, new_value, AD77681_GPIO2);
            pc.printf("\n Value %d successully written to GPIO2\n", new_value);
        } else
            pc.printf("\nInvalid value\n");         
        break;          
    case 5:
        pc.printf("Insert value to be written into GPIO3: ");
        ret = getUserInput(&new_value); 
            
        if (((new_value == GPIO_HIGH) || (new_value == GPIO_LOW)) && (ret == SUCCESS)) {
            ret_val = ad77681_gpio_write(device_adc, new_value, AD77681_GPIO3);
            pc.printf("\n Value %d successully written to GPIO3\n", new_value);
        } else
            pc.printf("\nInvalid value\n");         
        break;          
    default:
        pc.printf(" Invalid option\n");
        break;
    }   
}

/**
 * GPIO direction, part of the ADC_GPIO function
 *
 */
void static adc_GPIO_inout(void)
{
    uint32_t new_gpio_inout = 0, new_gpio_inout_set = 0;
    int32_t ret_val;
    
    pc.printf(" Set GPIOs as input or output: \n");
    pc.printf("  1 - Set all GPIOs\n");
    pc.printf("  2 - Set GPIO0\n");
    pc.printf("  3 - Set GPIO1\n");
    pc.printf("  4 - Set GIPO2\n");
    pc.printf("  5 - Set GPIO3\n");
    pc.printf(" Select an option: \n");
        
    getUserInput(&new_gpio_inout);  
    pc.putc('\n');
        
    switch (new_gpio_inout) {
    case 1:
        pc.printf("   1 - Set all GPIOS as inputs\n");
        pc.printf("   2 - Set all GPIOS as outputs\n");
            
        getUserInput(&new_gpio_inout_set);  
        pc.putc('\n');          
            
        if ((new_gpio_inout_set == 1) || (new_gpio_inout_set == 2)) {
            new_gpio_inout_set -= 1;
            new_gpio_inout_set *= 0xF;
            ret_val = ad77681_gpio_inout(device_adc, new_gpio_inout_set, AD77681_ALL_GPIOS);
            pc.printf("All GPIOs successfully set");
        } else
            pc.printf("\nInvalid value\n");         
        break;
    case 2:
        pc.printf("   1 - Set GPIO0 as input\n");
        pc.printf("   2 - Set GPIO0 as output\n");
            
        getUserInput(&new_gpio_inout_set);  
        pc.putc('\n');  
            
        if ((new_gpio_inout_set == 1) || (new_gpio_inout_set == 2)) {
            new_gpio_inout_set -= 1;
            ret_val = ad77681_gpio_inout(device_adc, new_gpio_inout_set, AD77681_GPIO0);
            pc.printf("GPIO0 successfully set");
        } else
            pc.printf("\nInvalid value\n");         
        break;          
    case 3:
        pc.printf("   1 - Set GPIO1 as input\n");
        pc.printf("   2 - Set GPIO1 as output\n");
            
        getUserInput(&new_gpio_inout_set);  
        pc.putc('\n');  
            
        if ((new_gpio_inout_set == 1) || (new_gpio_inout_set == 2)) {
            new_gpio_inout_set -= 1;
            ret_val = ad77681_gpio_inout(device_adc, new_gpio_inout_set, AD77681_GPIO1);
            pc.printf("GPIO1 successfully set");
        } else
            pc.printf("\nInvalid value\n");         
        break;          
    case 4:
        pc.printf("   1 - Set GPIO2 as input\n");
        pc.printf("   2 - Set GPIO2 as output\n");
            
        getUserInput(&new_gpio_inout_set);  
        pc.putc('\n');      
            
        if ((new_gpio_inout_set == 1) || (new_gpio_inout_set == 2)) {
            new_gpio_inout_set -= 1;
            ret_val = ad77681_gpio_inout(device_adc, new_gpio_inout_set, AD77681_GPIO2);
            pc.printf("GPIO2 successfully set");
        } else
            pc.printf("\nInvalid value\n");
        break;      
    case 5:
        pc.printf("   1 - Set GPIO3 as input\n");
        pc.printf("   2 - Set GPIO3 as output\n");
            
        getUserInput(&new_gpio_inout_set);  
        pc.putc('\n');  
            
        if ((new_gpio_inout_set == 1) || (new_gpio_inout_set == 2)) {
            new_gpio_inout_set -= 1;
            ret_val = ad77681_gpio_inout(device_adc, new_gpio_inout_set, AD77681_GPIO3);
            pc.printf("GPIO3 successfully set");
        } else
            pc.printf("\nInvalid value\n");
        break;              
    default:
        pc.printf(" Invalid option\n");
        break;  
    }
}

/**
 * Additional GPIO settings, part of the ADC_GPIO function
 *
 */
void static adc_GPIO_settings(void)
{
    uint32_t new_gpio_settings = 0;
    
    pc.printf(" GPIO Settings: \n");
    pc.printf("  1 - Enable  all GPIOs (Global enble)\n"); 
    pc.printf("  2 - Disable all GPIOs (Global disable)\n");
    pc.printf("  3 - Set GPIO0 - GPIO2 as open drain\n");
    pc.printf("  4 - Set GPIO0 - GPIO2 as strong driver\n");
    pc.printf(" Select an option: \n");
        
    getUserInput(&new_gpio_settings);   
    pc.putc('\n');
        
    switch (new_gpio_settings) {
    case 1:
        ad77681_global_gpio(device_adc, AD77681_GLOBAL_GPIO_ENABLE);
        pc.printf(" Global GPIO enalbe bit enabled");
        break;
    case 2:
        ad77681_global_gpio(device_adc, AD77681_GLOBAL_GPIO_DISABLE);
        pc.printf(" Global GPIO enalbe bit disabled");
        break;
    default:
        pc.printf(" Invalid option\n");
        break;  
    }
}

/**
 * Read ADC status from status registers
 *
 */
 void static menu_12_read_master_status(void)
 {  
    uint8_t reg_read_buf[3];
    char binary_number[8];
    char ok[3] = { 'O', 'K' }, fault[6] = { 'F', 'A', 'U', 'L', 'T' };
    
    ad77681_status(device_adc, current_status);
    pc.putc('\n');
    pc.printf("== MASTER STATUS REGISER\n");
    pc.printf("Master error:          %s\n", ((current_status->master_error == 0) ? (ok) : (fault)));
    pc.printf("ADC error:             %s\n", ((current_status->adc_error == 0) ? (ok) : (fault)));
    pc.printf("Dig error:             %s\n", ((current_status->dig_error == 0) ? (ok) : (fault)));
    pc.printf("Ext. clock:            %s\n", ((current_status->adc_err_ext_clk_qual == 0) ? (ok) : (fault)));
    pc.printf("Filter saturated:      %s\n", ((current_status->adc_filt_saturated == 0) ? (ok) : (fault)));
    pc.printf("Filter not settled:    %s\n", ((current_status->adc_filt_not_settled == 0) ? (ok) : (fault)));
    pc.printf("SPI error:             %s\n", ((current_status->spi_error == 0) ? (ok) : (fault)));
    pc.printf("POR Flag:              %s\n", ((current_status->por_flag == 0) ? (ok) : (fault)));
    
    if (current_status->spi_error == 1) {
        pc.printf("\n== SPI DIAG STATUS REGISER\n");
        pc.printf("SPI ignore error:      %s\n", ((current_status->spi_ignore == 0) ? (ok) : (fault)));
        pc.printf("SPI clock count error: %s\n", ((current_status->spi_clock_count == 0) ? (ok) : (fault)));
        pc.printf("SPI read error:        %s\n", ((current_status->spi_read_error == 0) ? (ok) : (fault)));
        pc.printf("SPI write error:       %s\n", ((current_status->spi_write_error == 0) ? (ok) : (fault)));
        pc.printf("SPI CRC error:         %s\n", ((current_status->spi_crc_error == 0) ? (ok) : (fault)));
    }
    if (current_status->adc_error == 1) {
        pc.printf("\n== ADC DIAG STATUS REGISER\n");
        pc.printf("DLDO PSM error:        %s\n", ((current_status->dldo_psm_error == 0) ? (ok) : (fault)));
        pc.printf("ALDO PSM error:        %s\n", ((current_status->aldo_psm_error == 0) ? (ok) : (fault)));
        pc.printf("REF DET error:         %s\n", ((current_status->ref_det_error == 0) ? (ok) : (fault)));
        pc.printf("FILT SAT error:        %s\n", ((current_status->filt_sat_error == 0) ? (ok) : (fault)));
        pc.printf("FILT NOT SET error:    %s\n", ((current_status->filt_not_set_error == 0) ? (ok) : (fault)));
        pc.printf("EXT CLK QUAL error:    %s\n", ((current_status->ext_clk_qual_error == 0) ? (ok) : (fault)));
    }   
    if (current_status->dig_error == 1) {
        pc.printf("\n== DIGITAL DIAG STATUS REGISER\n");
        pc.printf("Memory map CRC error:  %s\n", ((current_status->memoy_map_crc_error == 0) ? (ok) : (fault)));
        pc.printf("RAM CRC error:         %s\n", ((current_status->ram_crc_error == 0) ? (ok) : (fault)));
        pc.printf("FUSE CRC error:        %s\n", ((current_status->fuse_crc_error == 0) ? (ok) : (fault)));
    }   
    pc.putc('\n');
    print_prompt();
}

/**
 * Set Vref anc MCLK as "exteranl" values, depending on you setup
 *
 */
 void static menu_13_mclk_vref(void)
 {
    uint32_t input = 0, new_settings = 0;
    int32_t ret;
        
    pc.printf(" Set Vref and Mclk: \n");                                
    pc.printf("  1 - Change Vref\n"); 
    pc.printf("  2 - Change MCLK\n");
    pc.printf(" Select an option: \n");
    
    getUserInput(&new_settings);    
    pc.putc('\n');
    
    switch (new_settings) {
    case 1:
        pc.printf(" Change Vref from %d mV to [mV]: ", device_adc->vref);       // Vref change
        ret = getUserInput(&input); 
                
        if ((input >= 1000) && (input <= 5000) && (ret == SUCCESS)) {
            pc.printf("\n New Vref value is %d mV", input);
            device_adc->vref = input;
            
            #ifdef CN0540_ADI_FFT_H_
            // Update the Vref, Mclk and sampling rate
            update_FFT_enviroment(device_adc->vref, device_adc->mclk, device_adc->sample_rate, FFT_data); 
            #endif //CN0540_ADI_FFT_H_         
        } else
            pc.printf(" Invalid option\n"); 
        pc.putc('\n');
        break;      
    case 2:
        pc.printf(" Change MCLK from %d kHz to [kHz]: ", device_adc->mclk);     // MCLK change
        ret = getUserInput(&input);             
        
        if ((input >= 10000) && (input <= 50000) && (ret == SUCCESS)){
            pc.printf("\n New MCLK value is %d kHz\n", input);
            device_adc->vref = input;
            ad77681_update_sample_rate(device_adc);                             // Update the sample rate after changinig the MCLK
            
            #ifdef CN0540_ADI_FFT_H_
            // Update the Vref, Mclk and sampling rate
            update_FFT_enviroment(device_adc->vref, device_adc->mclk, device_adc->sample_rate, FFT_data); 
            #endif //CN0540_ADI_FFT_H_
        } else
            pc.printf(" Invalid option\n"); 
        pc.putc('\n');
        break;
    default:
        pc.printf(" Invalid option\n");
        break;
    }
    print_prompt();
}

/**
 * Print measured data and transfered to voltage
 *
 */
 void static menu_14_print_measured_data(void)
 {
    double voltage;
    int32_t shifted_data;
    uint16_t i;
    char buf[15];

    if (measured_data.finish) {
        // Printing Voltage
        pc.printf("\n\nVoltage\n");
        for ( i = 0; i < measured_data.samples; i++) {
            ad77681_data_to_voltage(device_adc, &measured_data.raw_data[i], &voltage);
            pc.printf("%.9f \n",voltage);
        }
        // Printing Codes
        pc.printf("\n\nCodes\n");
        for(i = 0 ; i < measured_data.samples ; i++) {
            if (measured_data.raw_data[i] & 0x800000)
                shifted_data = (int32_t)((0xFF << 24) | measured_data.raw_data[i]);
            else
                shifted_data = (int32_t)((0x00 << 24) | measured_data.raw_data[i]);
            pc.printf("%d\n", shifted_data + AD7768_HALF_SCALE);
        }
        // Printing Raw Date
        pc.printf("\n\nRaw data\n");
        for (i = 0; i < measured_data.samples; i++)
            pc.printf("%d\n", measured_data.raw_data[i]);
        // Set  measured_data.finish to false after Printing
        measured_data.finish = false;
    } else
        pc.printf("Data not prepared\n");
    print_prompt();
}

/**
 * Set data output mode
 *
 */
void static menu_15_set_adc_data_output_mode(void) 
{
    uint32_t new_data_mode = 0, new_length = 0, new_status = 0, new_crc = 0, ret;
    
    pc.printf(" ADC data outpup modes: \n");
    pc.printf("  1 - Continuous: waiting for DRDY\n");
    pc.printf("  2 - Continuous one shot: waiting for SYNC_IN\n");
    pc.printf("  3 - Single-conversion standby\n");
    pc.printf("  4 - Periodic standby\n");
    pc.printf("  5 - Standby mode\n");
    pc.printf("  6 - 16bit or 24bit data format\n");
    pc.printf("  7 - Status bit output\n");
    pc.printf("  8 - Switch form diag mode to measure\n");
    pc.printf("  9 - Switch form measure to diag mode\n");
    pc.printf(" 10 - Set CRC type\n");
    pc.printf(" Select an option: \n");
    
    getUserInput(&new_data_mode);
    pc.putc('\n');
    
    switch (new_data_mode) {
    case 1:
        ad77681_set_conv_mode(device_adc, AD77681_CONV_CONTINUOUS, device_adc->diag_mux_sel, device_adc->conv_diag_sel);// DIAG MUX NOT SELECTED
        pc.printf(" Continuous mode set\n");
        break;
    case 2:
        ad77681_set_conv_mode(device_adc, AD77681_CONV_ONE_SHOT, device_adc->diag_mux_sel, device_adc->conv_diag_sel);
        pc.printf(" Continuous one shot conversion set\n");
        break;
    case 3:
        ad77681_set_conv_mode(device_adc, AD77681_CONV_SINGLE, device_adc->diag_mux_sel, device_adc->conv_diag_sel);
        pc.printf(" Single conversion standby mode set\n");
        break;  
    case 4:
        ad77681_set_conv_mode(device_adc, AD77681_CONV_PERIODIC, device_adc->diag_mux_sel, device_adc->conv_diag_sel);
        pc.printf(" Periodiec standby mode set\n");
        break;  
    case 5:
        ad77681_set_conv_mode(device_adc, AD77681_CONV_STANDBY, device_adc->diag_mux_sel, device_adc->conv_diag_sel);
        pc.printf(" Standby mode set\n");
        break;
    case 6:
        pc.printf(" Conversion length select: \n");
        pc.printf("  1 - 24bit length\n");
        pc.printf("  2 - 16bit length\n");
        
        getUserInput(&new_length);
        pc.putc('\n');
        
        switch (new_length) {
        case 1:
            ad77681_set_convlen(device_adc, AD77681_CONV_24BIT);
            pc.printf(" 24bit data output format selected\n");
            break;
        case 2:
            ad77681_set_convlen(device_adc, AD77681_CONV_16BIT);
            pc.printf(" 16bit data output format selected\n");
            break;
        default:
            pc.printf(" Invalid option\n");
            break;
        }
        break;
    case 7:
        pc.printf(" Status bit output: \n");
        pc.printf("  1 - Enable status bit after each ADC conversion\n");
        pc.printf("  2 - Disable status bit after each ADC conversion\n");
        
        getUserInput(&new_status);
        pc.putc('\n');
        
        switch (new_status) {
        case 1:
            ad77681_set_status_bit(device_adc, true);
            pc.printf(" Status bit enabled\n");
            break;
        case 2:
            ad77681_set_status_bit(device_adc, false);
            pc.printf(" Status bit disabled\n");
            break;
        default:
            pc.printf(" Invalid option\n");
            break;
        }       
        break;
    case 8:
        ad77681_set_conv_mode(device_adc, device_adc->conv_mode, device_adc->diag_mux_sel, false);// DIAG MUX NOT SELECTED
        pc.printf(" Measure mode selected\n");
        break;
    case 9:
        ad77681_set_conv_mode(device_adc, device_adc->conv_mode, device_adc->diag_mux_sel, true); // DIAG MUX SELECTED
        pc.printf(" Diagnostic mode selected\n");
        break;
    case 10:
        pc.printf(" CRC settings \n");
        pc.printf("  1 - Disable CRC\n");
        pc.printf("  2 - 8-bit polynomial CRC\n");
        pc.printf("  3 - XOR based CRC\n");
        
        getUserInput(&new_crc);
        pc.putc('\n');
        
        switch (new_crc) {
        case 1:
            ad77681_set_crc_sel(device_adc, AD77681_NO_CRC);
            pc.printf(" CRC disabled\n");
            break;
        case 2:
            ad77681_set_crc_sel(device_adc, AD77681_CRC);
            pc.printf("  8-bit polynomial CRC method selected\n");
            break;
        case 3:
            ad77681_set_crc_sel(device_adc, AD77681_XOR);
            pc.printf("  XOR based CRC method selected\n");
            break;
        default:
            pc.printf(" Invalid option\n");
            break;
        }
        break;      
    default:
        pc.printf(" Invalid option\n");
        break;
    }
    print_prompt();
}

/**
 * Set diagnostic mode
 *
 */
void static menu_16_set_adc_diagnostic_mode(void)
{
    uint32_t new_diag_mode = 0; 
        
    pc.printf(" ADC diagnostic modes: \n");
    pc.printf("  1 - Internal temperature sensor\n");
    pc.printf("  2 - AIN shorted\n");
    pc.printf("  3 - Positive full-scale\n");
    pc.printf("  4 - Negative full-scale\n");
    pc.printf(" Select an option: \n");
    
    getUserInput(&new_diag_mode);
    pc.putc('\n');
    
    switch (new_diag_mode) {
    case 1:
        ad77681_set_conv_mode(device_adc, device_adc->conv_mode, AD77681_TEMP_SENSOR, true);          
        pc.printf(" Diagnostic mode: Internal temperature sensor selected\n");
        break;
    case 2:
        ad77681_set_conv_mode(device_adc, device_adc->conv_mode, AD77681_AIN_SHORT, true);
        pc.printf(" Diagnostic mode: AIN shorted selected\n");
        break;
    case 3:
        ad77681_set_conv_mode(device_adc, device_adc->conv_mode, AD77681_POSITIVE_FS, true);
        pc.printf(" Diagnostic mode: Positive full-scale selected\n");
        break;  
    case 4:
        ad77681_set_conv_mode(device_adc, device_adc->conv_mode, AD77681_NEGATIVE_FS, true);
        pc.printf(" Diagnostic mode: Negative full-scale selected\n");
        break;  
    default:
        pc.printf(" Invalid option\n");
        break;
    }
    print_prompt();
}

/**
 * Do the FFT
 *
 */
void static menu_17_do_the_fft(void)
{
    pc.printf(" FFT in progress...\n");
    measured_data.samples = FFT_data->fft_length * 2;
    measured_data.samples = 4096;
    measured_data.finish = false;
    measured_data.count = 0;
    pc.printf("Sampling....\n");
    cont_sampling();
    perform_FFT(measured_data.raw_data, FFT_data, FFT_meas, device_adc->sample_rate);
    pc.printf(" FFT Done!\n");
    measured_data.finish = false;   
    
    pc.printf("\n THD:\t\t%.3f dB", FFT_meas->THD);
    pc.printf("\n SNR:\t\t%.3f dB", FFT_meas->SNR);
    pc.printf("\n DR:\t\t%.3f dB", FFT_meas->DR);
    pc.printf("\n Fundamental:\t%.3f dBFS", FFT_meas->harmonics_mag_dbfs[0]);
    pc.printf("\n Fundamental:\t%.3f Hz", FFT_meas->harmonics_freq[0]*FFT_data->bin_width);
    pc.printf("\n RMS noise:\t%.6f uV", FFT_meas->RMS_noise * 1000000.0);
    pc.printf("\n LSB noise:\t%.3f", FFT_meas->transition_noise_LSB);
    
    print_prompt(); 
}

/**
 * Setting of the FFT module
 *
 */
void static menu_18_fft_settings(void)
{
    uint32_t new_menu_select, new_window, new_sample_count;
    
    pc.printf(" FFT settings: \n");
    pc.printf("  1 - Set window type\n");
    pc.printf("  2 - Set sample count\n");
    pc.printf("  3 - Print FFT plot\n");
    pc.printf(" Select an option: \n\n");
    
    getUserInput(&new_menu_select);
    
    switch (new_menu_select) {
    case 1:
        pc.printf(" Choose window type:\n");
        pc.printf("  1 - 7-term Blackman-Harris\n");
        pc.printf("  2 - Rectangular\n");
        
        getUserInput(&new_window);
        
        switch (new_window) {
        case 1:
            pc.printf("  7-7-term Blackman-Harris window selected\n");
            FFT_data->window = BLACKMAN_HARRIS_7TERM;
            break;          
        case 2:
            pc.printf("  Rectalngular window selected\n");
            FFT_data->window = RECTANGULAR;
            break;          
        default:
            pc.printf(" Invalid option\n");
            break;
        }       
        break;  
    case 2:
        pc.printf(" Set sample count:\n");
        pc.printf("  1 - 4096 samples\n");
        pc.printf("  2 - 1024 samples\n");
        pc.printf("  3 - 256  samples\n");
        pc.printf("  4 - 64   samples\n");
        pc.printf("  5 - 16   samples\n");
        
        getUserInput(&new_sample_count);
        
        switch (new_sample_count) {
        case 1:
            pc.printf(" 4096 samples selected\n");
            FFT_init(4096, FFT_data);   // Update the FFT module with a new sample count
            break;
        case 2:
            pc.printf(" 1024 samples selected\n");
            FFT_init(1024, FFT_data);
            break;
        case 3:
            pc.printf(" 256 samples selected\n");
            FFT_init(256, FFT_data);
            break;
        case 4:
            pc.printf(" 64 samples selected\n");
            FFT_init(64, FFT_data);
            break;
        case 5:
            pc.printf(" 16 samples selected\n");
            FFT_init(16, FFT_data);
            break;
        default:
            pc.printf(" Invalid option\n");
            break;  
        }       
        break;      
    case 3:
        if (FFT_data->fft_done == true) {
            pc.printf(" Printing FFT plot in dB:\n");
            
            for (uint16_t i = 0; i < FFT_data->fft_length; i++)
                pc.printf("%.4f\n", FFT_data->fft_dB[i]);
        }
        else
            pc.printf(" Data not prepared\n");
        break;      
    default:
        pc.printf(" Invalid option\n");
        break;  
    }
    print_prompt(); 
}

/**
 * Set Gains and Offsets
 *
 */
void static menu_19_gains_offsets(void)
{
    uint32_t gain_offset, new_menu_select;
    int32_t ret;
    
    pc.printf(" Gains and Offsets settings: \n");
    pc.printf("  1 - Set gain\n");
    pc.printf("  2 - Set offset\n");
    pc.printf(" Select an option: \n");
    
    getUserInput(&new_menu_select);
    
    switch (new_menu_select) {
    case 1:
        pc.printf(" Insert new Gain value in decimal form\n");
        ret = getUserInput(&gain_offset);
        
        if ((gain_offset <= 0xFFFFFF) && (ret == SUCCESS)) {
            ad77681_apply_gain(device_adc, gain_offset);
            pc.printf(" Value %d has been successfully inserted to the Gain register\n", gain_offset);
        } else
            pc.printf(" Invalid value\n");      
        break;  
    case 2:
        pc.printf(" Insert new Offset value in decimal form\n");
        ret = getUserInput(&gain_offset);       
        if ((gain_offset <= 0xFFFFFF) && (ret == SUCCESS)) {
            ad77681_apply_offset(device_adc, gain_offset);
            pc.printf(" Value %d has been successfully inserted to the Offset register\n", gain_offset);
        } else
            pc.printf(" Invalid value\n");      
        break;      
    default:
        pc.printf(" Invalid option\n");
        break;  
    }   
    print_prompt();     
}

/**
 * Chceck read and write functionaity by writing to and reading from scratchpad register
 *
 */
void static menu_20_check_scratchpad(void)
{
    int32_t ret;
    uint32_t ret_val;
    uint32_t new_menu_select;
    uint8_t chceck_sequence;
    
    pc.printf(" Scratchpad check\n");
    pc.printf("  Insert 8bit number for scratchpad check: \n");
    
    ret = getUserInput(&new_menu_select);
    
    if ((new_menu_select <= 0xFF) && (new_menu_select >= 0) && (ret == SUCCESS)) {
        chceck_sequence = (uint8_t)(new_menu_select);
        ret_val = ad77681_scratchpad(device_adc, &chceck_sequence);
        pc.printf("  Insered sequence:  %d\n  Returned sequence: %d\n", new_menu_select, chceck_sequence);
        if (ret_val == SUCCESS)
            pc.printf("  SUCCESS!\n");
        else
            pc.printf("  FAILURE!\n");
    } else
        pc.printf("  Invalid value\n"); 
    print_prompt(); 
}

/**
 * Start with the piezo accelerometer offset compensation
 * The offset compenzation process uses a successive approximation model
 * There is lot of averaging going on, because of quite noisy piezo accelerometer
 * It will take some time
 */
void static menu_21_piezo_offset(void)
{
    uint8_t ltc2606_res = 16;
    uint32_t dac_code = 0;
    uint32_t dac_code_arr[16];
    double mean_voltage = 0.0, min_voltage; 
    double mean_voltage_arr[16];
    int8_t sar_loop, min_find, min_index;
    uint16_t SINC3_odr;    

    // Low power mode and MCLK/16
    ad77681_set_power_mode(device_adc, AD77681_ECO);
    ad77681_set_mclk_div(device_adc, AD77681_MCLK_DIV_16); 
    
    // 4SPS = 7999 SINC3, 10SPS = 3199 SINC3, 50SPS = 639 SINC3
    ad77681_SINC3_ODR(device_adc, &SINC3_odr, 4);  
    // Set the oversamplig ratio to high value, to extract DC                                                                       
    ad77681_set_filter_type(device_adc, AD77681_SINC5_FIR_DECx32, AD77681_SINC3, SINC3_odr);
 
    // successive approximation algorithm
    pc.printf("\nInitialize SAR loop (DAC MSB set to high)\n");
    // Set DAC code to half scale  
    dac_code = (1 << (ltc2606_res - 1 ));
    // Update output of the DAC
    ltc26x6_write_code(device_dac, write_update_command, dac_code);
    // Wait for DAC output to settle                                    
    wait_ms(500);
    // Set desired number of samples for every iteration           
    measured_data.samples = 100;
    measured_data.finish = false;
    measured_data.count = 0;
    // Take X number of samples
    cont_sampling();
    // Get the mean voltage of taken samples stroed in the measured_data strucutre                                                                 
    get_mean_voltage(&measured_data, &mean_voltage);
    // Print the mean ADC read voltage for a given DAC code 
    pc.printf("DAC code:%x\t\tMean Voltage: %.6f\n", dac_code, mean_voltage);
    // Store the initial DAC code in the array
    dac_code_arr[ltc2606_res - 1] = dac_code;
    // Store the initial mean voltage in the array
    mean_voltage_arr[ltc2606_res - 1] = mean_voltage;
    
    for ( sar_loop = ltc2606_res - 1; sar_loop > 0; sar_loop--) {
        // Check if the mean voltage is positive or negative
        if (mean_voltage > 0) {
            dac_code = dac_code + (1 << (sar_loop - 1));
            pc.printf("UP\n\n");           
        } else {
            dac_code = dac_code - (1 << (sar_loop)) + (1 << (sar_loop-1));
            pc.printf("DOWN\n\n");        
        }  
        // Print loop coard
        pc.printf("SAR loop #: %d\n",sar_loop);
        // Update output of the DAC
        ltc26x6_write_code(device_dac, write_update_command, dac_code);
        // Wait for DAC output to settle                                    
        wait_ms(500);
        // Clear data finish flag
        measured_data.finish = false;
        measured_data.count = 0;
        // Take X number of samples
        cont_sampling();
        // Get the mean voltage of taken samples stroed in the measured_data strucutre                                                                 
        get_mean_voltage(&measured_data, &mean_voltage); 
        pc.printf("DAC code:%x\t\tMean Voltage: %.6f\n", dac_code, mean_voltage); 
        dac_code_arr[sar_loop - 1] = dac_code;
        mean_voltage_arr[sar_loop - 1] = mean_voltage;
    }
    min_voltage = abs(mean_voltage_arr[0]); 
    for (min_find = 0;  min_find < 16; min_find++) {
        if (min_voltage > abs(mean_voltage_arr[min_find])) {
            min_voltage = abs(mean_voltage_arr[min_find]);
            min_index = min_find;
        } 
    }
    ltc26x6_write_code(device_dac, write_update_command, dac_code_arr[min_index]);
    // Wait for DAC output to settle                                    
    wait_ms(500);
    // Print the final DAC code               
    pc.printf("\nFinal DAC code set to:%x\t\tFinal Mean Voltage: %.6f\n", dac_code_arr[min_index], mean_voltage_arr[min_index]);                
    // Set to original filter
    ad77681_set_filter_type(device_adc, AD77681_SINC5_FIR_DECx32, AD77681_FIR, 0);
    ad77681_update_sample_rate(device_adc);      
    pc.printf("\nOffset compenzation done!\n"); 
    print_prompt(); 
}

/**
 * Get mean from sampled data
 * @param mean_voltage      Mean Voltage
 * @param measured_data     The structure carying measured data
 */
void static get_mean_voltage(struct adc_data *measured_data, double *mean_voltage)
{
    int32_t shifted_data;
    double sum = 0, voltage = 0;
    uint16_t i;
    
    for ( i = 0; i < measured_data->samples; i++) {
        ad77681_data_to_voltage(device_adc, &measured_data->raw_data[i], &voltage);
        sum += voltage; 
    }
    *mean_voltage = (double)(sum / (double)(measured_data->samples));    
}

/**
 * Set output of the on-board DAC in codes or in voltage
 *
 */
void static menu_22_set_DAC_output(void)
{
    int16_t dac_status;
    uint16_t  code ;
    uint32_t new_menu_select, new_dac;
    float dac_voltage;
    // Gain factor of the on-board DAC buffer, to have full 5V range(ADA4807-1ARJZ)
    // Non-inverting op-amp resistor ratio => 1 + (2.7 k ohm / 2.7 k ohm)
    float buffer_gain =  2;  
    
    pc.printf(" Set DAC output: \n");
    pc.printf("  1 - Voltage\n");
    pc.printf("  2 - Codes\n");
    pc.printf(" Select an option: \n");
    
    getUserInput(&new_menu_select);
    
    switch (new_menu_select) {
    case 1:
        pc.printf(" Set DAC output in mV: ");
        getUserInput(&new_dac);
        
        dac_voltage = ((float)(new_dac) / 1000.0) / buffer_gain;
        ltc26x6_voltage_to_code(device_dac, dac_voltage, &code);    
        ltc26x6_write_code(device_dac, write_update_command, code); 
        if (dac_status == SUCCESS)    
            pc.printf("%.3f V at Shift output\n\n", dac_voltage * buffer_gain); 
        else if (dac_status == LTC26X6_CODE_OVERFLOW)
            pc.printf("%.3f V at Shift output, OVERFLOW!\n\n", dac_voltage * buffer_gain);  
        else if (dac_status == LTC26X6_CODE_UNDERFLOW)
            pc.printf("%.3f V at Shift output, UNDERFLOW!\n\n", dac_voltage * buffer_gain);     
        break;      
    case 2:
        pc.printf(" Set DAC codes in decimal form: ");
        getUserInput(&new_dac);             
        ltc26x6_write_code(device_dac, write_update_command, new_dac);
        pc.printf("%x at DAC output\n\n", new_dac);     
        break;
    default:
        pc.printf(" Invalid option\n");
        break;          
    }
    print_prompt();
}

/**
 * Prints out an array in binary form
 *
 */
void static print_binary(uint8_t number, char *binary_number)
{   
    for (int8_t i = 7; i >= 0; i--) {
        if (number & 1)
            binary_number[i] = '1';
        else
            binary_number[i] = '0';
        number >>= 1;
    }
}

/**
 * Setup SDP-K1 GPIOs
 * 
 * 
 */
 void static sdpk1_gpio_setup(void)
{
    // Enable DAC buffer & other buffer
    buffer_en = GPIO_HIGH;
    // Turn on onboard red LED
    led_red = GPIO_HIGH;
    // Turn on onboard blue LED
    led_blue = GPIO_HIGH;
}