MSP432 DAC8555
4チャンネルの16bitDACのDAC8555をMSPから制御
特徴はバッファを2つもっていて、同時に4つチャンネルを変更することもできる点。
https://www.tij.co.jp/jp/lit/ds/symlink/dac8555.pdf?ts=1623402965967&ref_url=https%253A%252F%252Fwww.tij.co.jp%252Fproduct%252Fjp%252FDAC8555
データシートを見ながら、電源回りにパスコン等をつけて回路を形成。Vrefには、
ISL21080CIH315Z-TK(基準電圧1.5V)を利用し動作確認をしている。
【動作】
LD1,LD0の組み合わせで、チャンネル1~4までまずはデータを送ってから、同時に電圧出力を変化させる事もできるし、各チャンネルを個別に次々に電圧を変更していく事もできる。このあたりは、データシートに任せて、後者で実装する。この時、LD0=0,LD=1にすることになる。DACSelect1,0は進数でチャンネルを設定するところ。PD0は、パワーモードの選択。DACなので特段苦労することはないかと。
/* Transmitting data to slave */
MAP_GPIO_setOutputLowOnPin(GPIO_PORT_P3, GPIO_PIN0);
MAP_SPI_transmitData(EUSCI_B0_BASE, Datatemp0);
MAP_SPI_transmitData(EUSCI_B0_BASE, Datatemp1);
MAP_SPI_transmitData(EUSCI_B0_BASE, Datatemp2);
MAP_GPIO_setOutputHighOnPin(GPIO_PORT_P3, GPIO_PIN0);
といったようにCSを下げてあげて、順番に送りこむ。
以下テストのソース
(利用するには、OLEDを使うための準備は必要→ここ)
動作としては、MSP432LaunchPadの横のスイッチを押すと、設定したい電圧を高くしたり、弱くしたりできて、出力されてくる電圧をADCで読み取ってOLEDに表示するというった内容。ADCは拡張性をもって5チャンネル程読めるようにしているが、コメントアウトして1つしか使っていない。
/* --COPYRIGHT--,BSD
* Copyright (c) 2017, Texas Instruments Incorporated
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* * Neither the name of Texas Instruments Incorporated nor the names of
* its contributors may be used to endorse or promote products derived
* from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
* EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
* --/COPYRIGHT--*/
/******************************************************************************
* MSP432 Empty Project
*
* Description: An empty project that uses DriverLib
*
* MSP432P401
* ------------------
* /|\| |
* | | |
* --|RST
* | SW1 /P1.1 |
* | SW2 /P1.4 |
* ******SPI*******
* | MOSI P/1.6 |------->
* | P1.7 |MISO
* <--- |P1.5 CLK |
* | CS/P3.0|------->
* ******I2C*******
* | SDA/P6.4|------->SSD1306*
* | SCK/P6.5|------->
* | |
* ******ADC14*******
* |ch1 P5.5 |
*
* DAC 8555
* ------------------
* |1 VoutA LDAC 16|connected to GND.when asynchronous DAC updates is used, triggered timing signal is given.
* |2 VoutB ENABLE 15|Active LOW.
* |3 Vref+ RSTSEL 14|Low zero, 1 half of Vref
* |4 Vcc RST 13|Active HIGH. RST is low, all DAC channels reset either to zero-scale (RSTSEL = 0) or midscale (RSTSEL = 1).
* |5 Vref- IOVdd 12|single-supply operation, it can be tied to AVDD.
* |6 GND DIN 11|
* |7 VoutC SCLK 10|
* |8 VoutD CS 9|
* ------------------
* Author:
*******************************************************************************/
/* DriverLib Includes */
#include <ti/devices/msp432p4xx/driverlib/driverlib.h>
/* Standard Includes */
#include <stdio.h>
#include <stdint.h>
#include <stdlib.h>
#include "ssd1306_lib.h"
char OLED_buffer[32];
static uint16_t resultsBuffer[5];
void DACVset(uint8_t chan, float Vsetadc);
/* SPI Master Configuration Parameter */
const eUSCI_SPI_MasterConfig spiMasterConfig =
{
EUSCI_B_SPI_CLOCKSOURCE_SMCLK, // SMCLK Clock Source
12000000, // SMCLK = DCO = 12000000
12000000, // SPICLK = 12000000
EUSCI_B_SPI_MSB_FIRST, // MSB First
EUSCI_B_SPI_PHASE_DATA_CHANGED_ONFIRST_CAPTURED_ON_NEXT,
//EUSCI_B_SPI_PHASE_DATA_CAPTURED_ONFIRST_CHANGED_ON_NEXT,
//EUSCI_B_SPI_CLOCKPOLARITY_INACTIVITY_HIGH, // High polarity
EUSCI_B_SPI_CLOCKPOLARITY_INACTIVITY_LOW, // Low polarity
EUSCI_SPI_3PIN
//EUSCI_SPI_4PIN_UCxSTE_ACTIVE_LOW // 3Wire SPI Mode
};
//DAC variables
static float Vset=1.0;
void DACVset(uint8_t chan, float Vsetadc);
uint16_t j;
int main(void)
{
/* Stop Watchdog */
MAP_WDT_A_holdTimer();
/**************************************************************************/
/*Switch*/
/**************************************************************************/
MAP_GPIO_setAsInputPinWithPullUpResistor(GPIO_PORT_P1, GPIO_PIN1);
MAP_GPIO_setAsInputPinWithPullUpResistor(GPIO_PORT_P1, GPIO_PIN4);
/**************************************************************************/
/*OLED SSD1306 via I2C*/
/**************************************************************************/
/* Initialization of SSD1306 OLED*/
ssd1306Init();
fillDisplay (0x00);
//draw6x8Str(0, 3, "Hello", 1,0);
/**************************************************************************/
/*ADC*/
/**************************************************************************/
/* for digital filter*/
//static float old_Vadc=0.000;
/* Setting reference voltage to 2.5 and enabling reference */
MAP_REF_A_setReferenceVoltage(REF_A_VREF2_5V);
MAP_REF_A_enableReferenceVoltage();
/* Initializing ADC (MCLK/1/1) */
MAP_ADC14_enableModule();
MAP_ADC14_initModule(ADC_CLOCKSOURCE_MCLK, ADC_PREDIVIDER_1, ADC_DIVIDER_1,0);
/* Configuring GPIOs for Analog In */
MAP_GPIO_setAsPeripheralModuleFunctionInputPin(GPIO_PORT_P5,
GPIO_PIN5 | GPIO_PIN4 | GPIO_PIN2 | GPIO_PIN1 | GPIO_PIN0,
GPIO_TERTIARY_MODULE_FUNCTION);
/* Configuring ADC Memory (ADC_MEM0 - ADC_MEM7 (A0 - A7) with no repeat)
* with internal 2.5v reference */
MAP_ADC14_configureMultiSequenceMode(ADC_MEM0, ADC_MEM7, false);
MAP_ADC14_configureConversionMemory(ADC_MEM0,
ADC_VREFPOS_INTBUF_VREFNEG_VSS,
ADC_INPUT_A0, false);//5.5
/* MAP_ADC14_configureConversionMemory(ADC_MEM1,
ADC_VREFPOS_INTBUF_VREFNEG_VSS,
ADC_INPUT_A1, false);//5.4
MAP_ADC14_configureConversionMemory(ADC_MEM3,
ADC_VREFPOS_INTBUF_VREFNEG_VSS,
ADC_INPUT_A3, false);//5.2
MAP_ADC14_configureConversionMemory(ADC_MEM4,
ADC_VREFPOS_INTBUF_VREFNEG_VSS,
ADC_INPUT_A4, false);//5.1
MAP_ADC14_configureConversionMemory(ADC_MEM5,
ADC_VREFPOS_INTBUF_VREFNEG_VSS,
ADC_INPUT_A5, false);//5.0*/
/* Enabling the interrupt when a conversion on channel 7 (end of sequence)
* is complete and enabling conversions */
MAP_ADC14_enableInterrupt(ADC_INT0);
/* Enabling Interrupts */
MAP_Interrupt_enableInterrupt(INT_ADC14);
MAP_Interrupt_enableMaster();
/* Setting up the sample timer to automatically step through the sequence
* convert.
*/
MAP_ADC14_enableSampleTimer(ADC_AUTOMATIC_ITERATION);
/* the start of the sample */
MAP_ADC14_enableConversion();
/**************************************************************************/
/* SPI setting*/
/**************************************************************************/
/* Setting DCO to 12MHz */
CS_setDCOCenteredFrequency(CS_DCO_FREQUENCY_12);
/* Selecting P1.5 P1.6 and P1.7 in SPI mode */
MAP_GPIO_setAsPeripheralModuleFunctionInputPin(GPIO_PORT_P1,
GPIO_PIN5 | GPIO_PIN6 | GPIO_PIN7, GPIO_PRIMARY_MODULE_FUNCTION);
/* Configuring SPI in 3wire master mode */
MAP_SPI_initMaster(EUSCI_B0_BASE, &spiMasterConfig);
/* Selecting P3.0 as SPI CS pin */
MAP_GPIO_setAsOutputPin(GPIO_PORT_P3, GPIO_PIN0);
MAP_GPIO_setOutputHighOnPin(GPIO_PORT_P3, GPIO_PIN0);
/* Enable SPI module */
MAP_SPI_enableModule(EUSCI_B0_BASE);
/**************************************************************************/
/* DAC8555 setting*/
/**************************************************************************/
DACVset(0, Vset);
DACVset(1, 0.1);
DACVset(2, 0.2);
DACVset(3, 0.3);
/**************************************************************************/
/*While Loop*/
/**************************************************************************/
float Vadc[5];
uint16_t i;
while(1){
while(MAP_GPIO_getInputPinValue(GPIO_PORT_P1, GPIO_PIN1)==GPIO_INPUT_PIN_LOW){
if ((Vset >= 0) && (Vset <= 1.4999)) {
Vset=Vset+0.0001;
sprintf (OLED_buffer, "%6.4f", Vset);
draw6x8Str(0, 1, OLED_buffer, 1,0);
DACVset(0, Vset);
}
}
while(MAP_GPIO_getInputPinValue(GPIO_PORT_P1, GPIO_PIN4)==GPIO_INPUT_PIN_LOW){
if ((Vset >= 0.0001) && (Vset <= 1.500)) {
Vset=Vset-0.0001;
sprintf (OLED_buffer, "%6.4f", Vset);
draw6x8Str(0, 1, OLED_buffer, 1,0);
DACVset(0, Vset);
}
}
//if (Vset>=1.5){Vset=0.0;}
DACVset(0, Vset);
//Vset=Vset+0.01;
MAP_ADC14_toggleConversionTrigger();
for (i=0;i<1;++i){
Vadc[i]=2.5*resultsBuffer[i]/ 16384;
}
//digital filtering
//Vadc[0]=0.8*old_Vadc+0.2*Vadc[0];
//old_Vadc=Vadc[0];
sprintf (OLED_buffer, "%6.4f", Vadc[0]);
draw6x8Str(0, 0, OLED_buffer, 1,0);
sprintf (OLED_buffer, "%6.4f", Vset);
draw6x8Str(0, 1, OLED_buffer, 1,0);
}
}
void ADC14_IRQHandler(void){
uint64_t status;
status = MAP_ADC14_getEnabledInterruptStatus();
MAP_ADC14_clearInterruptFlag(status);
if(status & ADC_INT0)
{
MAP_ADC14_getMultiSequenceResult(resultsBuffer);
}
}
void DACVset(uint8_t chan, float Vsetadc){
static uint16_t DataInt=0;
static uint8_t Datatemp0=0;
static uint8_t Datatemp1=0;
static uint8_t Datatemp2=0;
const float Vdacref=1.500;
//Send data to DAC8555 via SPI
DataInt=(uint16_t)(Vsetadc/Vdacref*65536);
switch(chan) {
case 0: //Channel A
Datatemp0 = 0b00010000;
break;
case 1: //Channel B
Datatemp0 = 0b00010010;
break;
case 2: //Channel C
Datatemp0 = 0b00010100;
break;
case 3: //Channel D
Datatemp0 = 0b00010110;
break;
default:
Datatemp0 = 0b00010000;
}
//Datatemp0=0b00010000;// control bits
Datatemp1=DataInt >> 8; //MSB
Datatemp2=DataInt & 0xFF; //LSB
/* Transmitting data to slave */
MAP_GPIO_setOutputLowOnPin(GPIO_PORT_P3, GPIO_PIN0);
MAP_SPI_transmitData(EUSCI_B0_BASE, Datatemp0);
MAP_SPI_transmitData(EUSCI_B0_BASE, Datatemp1);
MAP_SPI_transmitData(EUSCI_B0_BASE, Datatemp2);
MAP_GPIO_setOutputHighOnPin(GPIO_PORT_P3, GPIO_PIN0);
sprintf (OLED_buffer, "%x %x %x", Datatemp0,Datatemp1,Datatemp2);
draw6x8Str(0, 2, OLED_buffer, 1,0);
}
コメント
コメントを投稿