Completed and added pwmout_api

pull/1178/head
hjjeon0608 2015-06-11 16:32:58 +09:00
parent c6f7c5dc93
commit 60a87d97e7
12 changed files with 237 additions and 73 deletions

View File

@ -661,6 +661,15 @@ typedef struct
#define PWM_CH6 ((PWM_CHn_TypeDef *) (W7500x_PWM_BASE + 0x600UL))
#define PWM_CH7 ((PWM_CHn_TypeDef *) (W7500x_PWM_BASE + 0x700UL))
#define PWM_CH0_BASE (W7500x_PWM_BASE)
#define PWM_CH1_BASE (W7500x_PWM_BASE + 0x100UL)
#define PWM_CH2_BASE (W7500x_PWM_BASE + 0x200UL)
#define PWM_CH3_BASE (W7500x_PWM_BASE + 0x300UL)
#define PWM_CH4_BASE (W7500x_PWM_BASE + 0x400UL)
#define PWM_CH5_BASE (W7500x_PWM_BASE + 0x500UL)
#define PWM_CH6_BASE (W7500x_PWM_BASE + 0x600UL)
#define PWM_CH7_BASE (W7500x_PWM_BASE + 0x700UL)
#define RNG ((RNG_TypeDef *) W7500x_RNG_BASE)
#define SSP0 ((SSP_TypeDef*) (SSP0_BASE))

View File

@ -53,4 +53,8 @@ extern const PinMap PinMap_SPI_SCLK[];
extern const PinMap PinMap_SPI_MOSI[];
extern const PinMap PinMap_SPI_MISO[];
extern const PinMap PinMap_SPI_SSEL[];
//*** PWM ***
extern const PinMap PinMap_PWM[];
#endif

View File

@ -60,14 +60,15 @@ typedef enum {
I2C_1 = (int)I2C1_BASE
} I2CName;
typedef enum {
PWM_1 = 0
// PWM_1 = (int)TIM1_BASE,
// PWM_3 = (int)TIM3_BASE,
// PWM_14 = (int)TIM14_BASE,
// PWM_15 = (int)TIM15_BASE,
// PWM_16 = (int)TIM16_BASE,
// PWM_17 = (int)TIM17_BASE
typedef enum {
PWM_0 = (int)PWM_CH0_BASE,
PWM_1 = (int)PWM_CH1_BASE,
PWM_2 = (int)PWM_CH2_BASE,
PWM_3 = (int)PWM_CH3_BASE,
PWM_4 = (int)PWM_CH4_BASE,
PWM_5 = (int)PWM_CH5_BASE,
PWM_6 = (int)PWM_CH6_BASE,
PWM_7 = (int)PWM_CH7_BASE
} PWMName;
#ifdef __cplusplus

View File

@ -72,34 +72,56 @@ const PinMap PinMap_I2C_SCL[] = {
//*** SPI ***
const PinMap PinMap_SPI_SCLK[] = {
{PA_6 , SPI_0, 0},
{PB_1 , SPI_1, 0},
{PC_12, SPI_0, 3},
{PA_12, SPI_1, 3},
{PA_6 , SPI_0, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF0)},
{PB_1 , SPI_1, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF0)},
{PC_12, SPI_0, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF3)},
{PA_12, SPI_1, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF3)},
{NC , NC , 0}
};
const PinMap PinMap_SPI_MOSI[] = {
{PA_8 , SPI_0, 0},
{PB_3 , SPI_1, 0},
{PC_10, SPI_0, 3},
{PA_14, SPI_1, 3},
{PA_8 , SPI_0, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF0)},
{PB_3 , SPI_1, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF0)},
{PC_10, SPI_0, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF3)},
{PA_14, SPI_1, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF3)},
{NC , NC , 0}
};
const PinMap PinMap_SPI_MISO[] = {
{PA_7 , SPI_0, 0},
{PB_2 , SPI_1, 0},
{PC_11, SPI_0, 3},
{PA_13, SPI_1, 3},
{PA_7 , SPI_0, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF0)},
{PB_2 , SPI_1, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF0)},
{PC_11, SPI_0, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF3)},
{PA_13, SPI_1, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF3)},
{NC , NC , 0}
};
const PinMap PinMap_SPI_SSEL[] = {
{PA_5 , SPI_0, 0},
{PB_0 , SPI_1, 0},
{PC_13, SPI_0, 3},
{PA_11, SPI_1, 3},
{PA_5 , SPI_0, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF0)},
{PB_0 , SPI_1, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF0)},
{PC_13, SPI_0, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF3)},
{PA_11, SPI_1, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF3)},
{NC , NC , 0}
};
const PinMap PinMap_PWM[] = {
{PA_0 , PWM_6, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF2)},
{PA_1 , PWM_7, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF2)},
{PA_5 , PWM_2, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF3)},
{PA_6 , PWM_3, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF3)},
{PA_7 , PWM_4, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF3)},
{PA_8 , PWM_5, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF3)},
{PA_9 , PWM_6, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF3)},
{PA_10, PWM_7, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF3)},
{PC_0 , PWM_0, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF2)},
{PC_1 , PWM_1, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF2)},
{PC_2 , PWM_2, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF2)},
{PC_3 , PWM_3, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF2)},
{PC_4 , PWM_4, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF2)},
{PC_5 , PWM_5, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF2)},
{PC_8 , PWM_0, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF0)},
{PC_9 , PWM_1, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF0)},
{PC_10, PWM_2, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF2)},
{PC_11, PWM_3, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF2)},
{NC , NC , WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF0)}
};

View File

@ -39,10 +39,10 @@ extern "C" {
// See W7500x_hal_gpio.h for values of MODE, PUPD and AFNUM
#define WIZ_PIN_DATA(MODE, PUPD, AFNUM) ((int)(((AFNUM) << 8) | ((PUPD) << 4) | ((MODE) << 0)))
#define WIZ_PIN_MODE(X) (((X) >> 0) & 0x0F)
#define WIZ_PIN_DATA(MODE, PUPD, AFNUM) ((int)(((MODE) << 8) | ((PUPD) << 4) | ((AFNUM) << 0)))
#define WIZ_PIN_PUPD(X) (((X) >> 4) & 0x0F)
#define WIZ_PIN_AFNUM(X) (((X) >> 8) & 0x0F)
#define WIZ_PIN_AFNUM(X) (((X) >> 0) & 0x0F)
#define WIZ_PIN_MODE(X) (((X) >> 8) & 0x0F)
#define WIZ_MODE_INPUT (0)
#define WIZ_MODE_OUTPUT (1)
#define WIZ_MODE_AF (2)
@ -65,8 +65,7 @@ typedef enum {
typedef enum {
// W7500x Pin Names (AF[9:8] + PORT[5:4] + PIN[3:0])
// W7500x PORT[5:4] + PIN[3:0])
PA_0 = 0x000,
PA_1 = 0x001,
PA_2 = 0x002,
@ -83,7 +82,7 @@ typedef enum {
PA_13 = 0x00D,
PA_14 = 0x00E,
PA_15 = 0x00F,
PB_0 = 0x010, //SSEL1/SD_SEL
PB_1 = 0x011, //SCLK1/SD_CLK
PB_2 = 0x012, //MISO1/SD_MISO
@ -185,7 +184,6 @@ typedef enum {
PullNone = 0,
PullDown = 1,
PullUp = 2,
OpenDrain = 3,
PullDefault = PullNone
} PinMode;

View File

@ -50,7 +50,7 @@
#define DEVICE_RTC 0
#define DEVICE_PWMOUT 0
#define DEVICE_PWMOUT 1
#define DEVICE_SLEEP 0

View File

@ -87,10 +87,11 @@ struct i2c_s {
};
struct pwmout_s {
PWMName pwm;
PWM_CHn_TypeDef * PWM_CHx;
PinName pin;
uint32_t period;
uint32_t pulse;
uint32_t PrescalerValue;
};
#include "gpio_object.h"

View File

@ -59,6 +59,7 @@ void gpio_init(gpio_t *obj, PinName pin)
void gpio_mode(gpio_t *obj, PinMode mode)
{
pin_mode(obj->pin, mode);
obj->mode = mode;
}
void gpio_dir(gpio_t *obj, PinDirection direction)
@ -66,9 +67,5 @@ void gpio_dir(gpio_t *obj, PinDirection direction)
MBED_ASSERT(obj->pin != (PinName)NC);
obj->direction = direction;
if (direction == PIN_OUTPUT) {
pin_function(obj->pin, WIZ_PIN_DATA(WIZ_MODE_OUTPUT, WIZ_GPIO_NOPULL, 1));
} else { // PIN_INPUT
pin_function(obj->pin, WIZ_PIN_DATA(WIZ_MODE_INPUT, WIZ_GPIO_NOPULL, 1));
}
pin_function(obj->pin, WIZ_PIN_DATA(obj->direction, obj->mode, 1));
}

View File

@ -42,6 +42,7 @@ typedef struct {
uint32_t pin_index;
uint32_t port_num;
uint32_t direction;
uint32_t mode;
__IO uint32_t *reg_data_in;
} gpio_t;

View File

@ -63,8 +63,8 @@ void i2c_init(i2c_t *obj, PinName sda, PinName scl)
// Configure I2C pins
pinmap_pinout(sda, PinMap_I2C_SDA);
pinmap_pinout(scl, PinMap_I2C_SCL);
pin_mode(sda, OpenDrain);
pin_mode(scl, OpenDrain);
pin_mode(sda, PullUp);
pin_mode(scl, PullUp);
}
// Enable I2C2 clock and pinout if not done
@ -73,8 +73,8 @@ void i2c_init(i2c_t *obj, PinName sda, PinName scl)
// Configure I2C pins
pinmap_pinout(sda, PinMap_I2C_SDA);
pinmap_pinout(scl, PinMap_I2C_SCL);
pin_mode(sda, OpenDrain);
pin_mode(scl, OpenDrain);
pin_mode(sda, PullUp);
pin_mode(scl, PullUp);
}
// Reset to clear pending flags if any

View File

@ -31,17 +31,9 @@
#include "mbed_assert.h"
#include "pinmap.h"
#include "PortNames.h"
#include "mbed_error.h"
// GPIO mode look-up table
// It have to same with PinMode index in "PinNames.h"
static const uint32_t gpio_pupd[4] = {
GPIO_NO_PUPD, // PullNone
GPIO_PuPd_DOWN, // PullDown
GPIO_PuPd_UP, // PullUp
GPIO_OD // OpenDrain
};
uint32_t Get_GPIO_BaseAddress(uint32_t port_idx)
{
uint32_t gpio_add = 0;
@ -65,7 +57,6 @@ uint32_t Get_GPIO_BaseAddress(uint32_t port_idx)
return gpio_add;
}
/**
* Configure pin (input, output, alternate function or analog) + output speed + AF
*/
@ -79,24 +70,23 @@ void pin_function(PinName pin, int data) {
uint32_t port_num = WIZ_PORT(pin);
uint32_t pin_index = WIZ_PIN_INDEX(pin);
uint32_t gpio_add = Get_GPIO_BaseAddress(port_num);
GPIO_TypeDef *gpio = (GPIO_TypeDef *)gpio_add;
GPIO_TypeDef *gpio;
// Configure Alternate Function
// Warning: Must be done before the GPIO is initialized
switch (afnum) {
case 0:
HAL_PAD_AFConfig(port_num, pin_index,Px_AFSR_AF0);
HAL_PAD_AFConfig((PAD_Type)port_num, (uint16_t)pin_index, (PAD_AF_TypeDef)Px_AFSR_AF0);
break;
case 1:
HAL_PAD_AFConfig(port_num, pin_index,Px_AFSR_AF1);
HAL_PAD_AFConfig((PAD_Type)port_num, (uint16_t)pin_index, (PAD_AF_TypeDef)Px_AFSR_AF1);
break;
case 2:
HAL_PAD_AFConfig(port_num, pin_index,Px_AFSR_AF2);
HAL_PAD_AFConfig((PAD_Type)port_num, (uint16_t)pin_index, (PAD_AF_TypeDef)Px_AFSR_AF2);
break;
case 3:
HAL_PAD_AFConfig(port_num, pin_index,Px_AFSR_AF3);
HAL_PAD_AFConfig((PAD_Type)port_num, (uint16_t)pin_index, (PAD_AF_TypeDef)Px_AFSR_AF3);
break;
default:
break;
@ -106,10 +96,12 @@ void pin_function(PinName pin, int data) {
return;
// Configure GPIO
gpio = (GPIO_TypeDef *)Get_GPIO_BaseAddress(port_num);
GPIO_InitTypeDef GPIO_InitStructure;
GPIO_InitStructure.GPIO_Pin = pin_index;
GPIO_InitStructure.GPIO_Mode = mode;
GPIO_InitStructure.GPIO_Pad = gpio_pupd[pupd];
GPIO_InitStructure.GPIO_Mode = (GPIOMode_TypeDef)mode;
GPIO_InitStructure.GPIO_Pad = (GPIOPad_TypeDef)pupd;
HAL_GPIO_Init(gpio, &GPIO_InitStructure);
}
@ -119,30 +111,25 @@ void pin_function(PinName pin, int data) {
void pin_mode(PinName pin, PinMode pupd)
{
MBED_ASSERT(pin != (PinName)NC);
P_Port_Def *px_pcr;
uint32_t port_num = WIZ_PORT(pin);
uint32_t pin_num = WIZ_PIN_NUM(pin);
switch(port_num) {
case PortA:
px_pcr = PA_PCR;
PA_PCR->Port[pin_num] |= pupd;
break;
case PortB:
px_pcr = PB_PCR;
PB_PCR->Port[pin_num] |= pupd;
break;
case PortC:
px_pcr = PC_PCR;
PC_PCR->Port[pin_num] |= pupd;
break;
case PortD:
px_pcr = (P_Port_Def*)PD_PCR;
PD_PCR->Port[pin_num] |= pupd;
break;
default:
error("Pinmap error: wrong port number.");
error("Pinmap error: wrong port number.");
return;
}
px_pcr->Port[port_num] &= ~(Px_PCR_PUPD_DOWN|Px_PCR_PUPD_UP|Px_PCR_DS_HIGH| \
Px_PCR_OD | Px_PCR_IE | Px_PCR_CS_SUMMIT);
px_pcr->Port[port_num] |= gpio_pupd[pupd];
}

View File

@ -0,0 +1,144 @@
/* mbed Microcontroller Library
*******************************************************************************
* Copyright (c) 2015 WIZnet Co.,Ltd. All rights reserved.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice,
* this list of conditions and the following disclaimer.
* 2. 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.
* 3. Neither the name of ARM Limited 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 HOLDER 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.
*******************************************************************************
*/
#include "pwmout_api.h"
#if DEVICE_PWMOUT
#include "cmsis.h"
#include "pinmap.h"
#include "mbed_error.h"
#include "PeripheralPins.h"
static PWM_TimerModeInitTypeDef TimerModeStructure;
void pwmout_init(pwmout_t* obj, PinName pin)
{
// Get the peripheral name from the pin and assign it to the object
obj->PWM_CHx = (PWM_CHn_TypeDef *)pinmap_peripheral(pin, PinMap_PWM);
if (obj->PWM_CHx == (PWM_CHn_TypeDef *)NC) {
error("PWM error: pinout mapping failed.");
}
// Configure GPIO
pinmap_pinout(pin, PinMap_PWM);
GetSystemClock();
obj->pin = pin;
pwmout_period_us(obj, 20000); // 20 ms per default
}
void pwmout_free(pwmout_t* obj)
{
// Configure GPIO
pin_function(obj->pin, WIZ_PIN_DATA(WIZ_MODE_AF, WIZ_GPIO_NOPULL, Px_AFSR_AF0));
}
void pwmout_write(pwmout_t* obj, float value)
{
if (value < (float)0.0) {
value = 0.0;
} else if (value > (float)1.0) {
value = 1.0;
}
obj->pulse = (uint32_t)((float)obj->period * value);
PWM_CHn_Stop(obj->PWM_CHx);
TimerModeStructure.PWM_CHn_PR = obj->PrescalerValue - 1;
TimerModeStructure.PWM_CHn_MR = obj->pulse;
TimerModeStructure.PWM_CHn_LR = obj->period;
TimerModeStructure.PWM_CHn_UDMR = PWM_CHn_UDMR_UpCount;
TimerModeStructure.PWM_CHn_PDMR = PWM_CHn_PDMR_Periodic;
PWM_TimerModeInit(obj->PWM_CHx, &TimerModeStructure);
PWM_CHn_Start(obj->PWM_CHx);
}
float pwmout_read(pwmout_t* obj)
{
float value = 0;
if (obj->period > 0) {
value = (float)(obj->pulse) / (float)(obj->period);
}
return ((value > (float)1.0) ? (float)(1.0) : (value));
}
void pwmout_period(pwmout_t* obj, float seconds)
{
pwmout_period_us(obj, seconds * 1000000.0f);
}
void pwmout_period_ms(pwmout_t* obj, int ms)
{
pwmout_period_us(obj, ms * 1000);
}
void pwmout_period_us(pwmout_t* obj, int us)
{
PWM_CHn_Stop(obj->PWM_CHx);
// Update the SystemCoreClock variable
SystemCoreClockUpdate();
obj->period = (us * 2) - 1;
obj->pulse = us / 2;
obj->PrescalerValue = (SystemCoreClock / 1000000) / 2;
TimerModeStructure.PWM_CHn_PR = obj->PrescalerValue - 1;
TimerModeStructure.PWM_CHn_MR = obj->pulse;
TimerModeStructure.PWM_CHn_LR = obj->period;
TimerModeStructure.PWM_CHn_UDMR = PWM_CHn_UDMR_UpCount;
TimerModeStructure.PWM_CHn_PDMR = PWM_CHn_PDMR_Periodic;
PWM_TimerModeInit(obj->PWM_CHx, &TimerModeStructure);
PWM_CtrlPWMOutputEnable(obj->PWM_CHx);
}
void pwmout_pulsewidth(pwmout_t* obj, float seconds)
{
pwmout_pulsewidth_us(obj, seconds * 1000000.0f);
}
void pwmout_pulsewidth_ms(pwmout_t* obj, int ms)
{
pwmout_pulsewidth_us(obj, ms * 1000);
}
void pwmout_pulsewidth_us(pwmout_t* obj, int us)
{
float value = (float)(2 * us) / (float)obj->period;
pwmout_write(obj, value);
}
#endif