forked from zephyrproject-rtos/zephyr
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathpwm.h
147 lines (122 loc) · 3.5 KB
/
pwm.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
/*
* Copyright (c) 2016 Intel Corporation.
*
* SPDX-License-Identifier: Apache-2.0
*/
/**
* @file
* @brief Public PWM Driver APIs
*/
#ifndef ZEPHYR_INCLUDE_PWM_H_
#define ZEPHYR_INCLUDE_PWM_H_
/**
* @brief PWM Interface
* @defgroup pwm_interface PWM Interface
* @ingroup io_interfaces
* @{
*/
#ifdef __cplusplus
extern "C" {
#endif
#define PWM_ACCESS_BY_PIN 0
#define PWM_ACCESS_ALL 1
#include <errno.h>
#include <zephyr/types.h>
#include <stddef.h>
#include <device.h>
/**
* @typedef pwm_pin_set_t
* @brief Callback API upon setting the pin
* See @a pwm_pin_set_cycles() for argument description
*/
typedef int (*pwm_pin_set_t)(struct device *dev, u32_t pwm,
u32_t period_cycles, u32_t pulse_cycles);
/**
* @typedef pwm_get_cycles_per_sec_t
* @brief Callback API upon getting cycles per second
* See @a pwm_get_cycles_per_sec() for argument description
*/
typedef int (*pwm_get_cycles_per_sec_t)(struct device *dev, u32_t pwm,
u64_t *cycles);
/** @brief PWM driver API definition. */
struct pwm_driver_api {
pwm_pin_set_t pin_set;
pwm_get_cycles_per_sec_t get_cycles_per_sec;
};
/**
* @brief Set the period and pulse width for a single PWM output.
*
* @param dev Pointer to the device structure for the driver instance.
* @param pwm PWM pin.
* @param period Period (in clock cycle) set to the PWM. HW specific.
* @param pulse Pulse width (in clock cycle) set to the PWM. HW specific.
*
* @retval 0 If successful.
* @retval Negative errno code if failure.
*/
__syscall int pwm_pin_set_cycles(struct device *dev, u32_t pwm,
u32_t period, u32_t pulse);
static inline int _impl_pwm_pin_set_cycles(struct device *dev, u32_t pwm,
u32_t period, u32_t pulse)
{
struct pwm_driver_api *api;
api = (struct pwm_driver_api *)dev->driver_api;
return api->pin_set(dev, pwm, period, pulse);
}
/**
* @brief Get the clock rate (cycles per second) for a single PWM output.
*
* @param dev Pointer to the device structure for the driver instance.
* @param pwm PWM pin.
* @param cycles Pointer to the memory to store clock rate (cycles per sec).
* HW specific.
*
* @retval 0 If successful.
* @retval Negative errno code if failure.
*/
__syscall int pwm_get_cycles_per_sec(struct device *dev, u32_t pwm,
u64_t *cycles);
static inline int _impl_pwm_get_cycles_per_sec(struct device *dev, u32_t pwm,
u64_t *cycles)
{
struct pwm_driver_api *api;
api = (struct pwm_driver_api *)dev->driver_api;
return api->get_cycles_per_sec(dev, pwm, cycles);
}
/**
* @brief Set the period and pulse width for a single PWM output.
*
* @param dev Pointer to the device structure for the driver instance.
* @param pwm PWM pin.
* @param period Period (in micro second) set to the PWM.
* @param pulse Pulse width (in micro second) set to the PWM.
*
* @retval 0 If successful.
* @retval Negative errno code if failure.
*/
static inline int pwm_pin_set_usec(struct device *dev, u32_t pwm,
u32_t period, u32_t pulse)
{
u64_t period_cycles, pulse_cycles, cycles_per_sec;
if (pwm_get_cycles_per_sec(dev, pwm, &cycles_per_sec) != 0) {
return -EIO;
}
period_cycles = (period * cycles_per_sec) / USEC_PER_SEC;
if (period_cycles >= ((u64_t)1 << 32)) {
return -ENOTSUP;
}
pulse_cycles = (pulse * cycles_per_sec) / USEC_PER_SEC;
if (pulse_cycles >= ((u64_t)1 << 32)) {
return -ENOTSUP;
}
return pwm_pin_set_cycles(dev, pwm, (u32_t)period_cycles,
(u32_t)pulse_cycles);
}
#ifdef __cplusplus
}
#endif
/**
* @}
*/
#include <syscalls/pwm.h>
#endif /* ZEPHYR_INCLUDE_PWM_H_ */