summaryrefslogtreecommitdiff
path: root/include/host_command.h
blob: c9dcd3ddd811fd04e9f2ad5c7a2e82a3788e368a (plain)
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
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
/* Copyright (c) 2012 The Chromium OS Authors. All rights reserved.
 * Use of this source code is governed by a BSD-style license that can be
 * found in the LICENSE file.
 */

/* Host command module for Chrome EC */

#ifndef __CROS_EC_HOST_COMMAND_H
#define __CROS_EC_HOST_COMMAND_H

#include "common.h"
#include "ec_commands.h"

/* Args for host command handler */
struct host_cmd_handler_args {
	/*
	 * The driver that receives the command sets up the send_response()
	 * handler. Once the command is processed this handler is called to
	 * send the response back to the host.
	 */
	void (*send_response)(struct host_cmd_handler_args *args);
	uint16_t command;      /* Command (e.g., EC_CMD_FLASH_GET_INFO) */
	uint8_t version;       /* Version of command (0-31) */

	const void *params; /* Input parameters */
	uint16_t params_size;  /* Size of input parameters in bytes */

	/*
	 * Pointer to output response data buffer.  On input to the handler,
	 * points to a buffer of size response_max.
	 */
	void *response;

	/* Maximum size of response buffer provided to command handler */
	uint16_t response_max;

	/*
	 * Size of data pointed to by response.  Defaults to 0, so commands
	 * which do not produce response data do not need to set this.
	 */
	uint16_t response_size;

	/*
	 * This is the result returned by command and therefore the status to
	 * be reported from the command execution to the host. The driver
	 * should set this to EC_RES_SUCCESS on receipt of a valid command.
	 * It is then passed back to the driver via send_response() when
	 * command execution is complete. The driver may still override this
	 * when sending the response back to the host if it detects an error
	 * in the response or in its own operation.
	 */
	enum ec_status result;
};

/* Args for host packet handler */
struct host_packet {
	/*
	 * The driver that receives the command sets up the send_response()
	 * handler. Once the command is processed this handler is called to
	 * send the response back to the host.
	 */
	void (*send_response)(struct host_packet *pkt);

	/* Input request data */
	const void *request;

	/*
	 * Input request temp buffer.  If this is non-null, the data has not
	 * been copied from here into the request buffer yet.  The host command
	 * handler should do so while verifying the command.  The interface
	 * can't do it, because it doesn't know how much to copy.
	 */
	void *request_temp;

	/*
	 * Maximum size of request the interface can handle, in bytes.  The
	 * buffers pointed to by *request and *request_temp must be at least
	 * this big.
	 */
	uint16_t request_max;

	/* Size of input request data, in bytes */
	uint16_t request_size;

	/* Pointer to output response data buffer */
	void *response;

	/* Maximum size of response buffer provided to command handler */
	uint16_t response_max;

	/* Size of output response data, in bytes */
	uint16_t response_size;

	/*
	 * Error from driver; if this is non-zero, host command handler will
	 * return a properly formatted error response packet rather than
	 * calling a command handler.
	 */
	enum ec_status driver_result;
};

/* Host command */
struct host_command {
	/*
	 * Handler for the command.  Args points to context for handler.
	 * Returns result status (EC_RES_*).
	 */
	int (*handler)(struct host_cmd_handler_args *args);
	/* Command code */
	int command;
	/* Mask of supported versions */
	int version_mask;
};

/**
 * Return a pointer to the memory-mapped buffer.
 *
 * This buffer is EC_MEMMAP_SIZE bytes long, is writable at any time, and the
 * host can read it at any time.
 *
 * @param offset        Offset within the range to return
 * @return pointer to the buffer at that offset
 */
uint8_t *host_get_memmap(int offset);

/**
 * Process a host command and return its response
 *
 * @param args	        Command handler args
 * @return resulting status
 */
enum ec_status host_command_process(struct host_cmd_handler_args *args);

/**
 * Set one or more host event bits.
 *
 * @param mask          Event bits to set (use EC_HOST_EVENT_MASK()).
 */
void host_set_events(uint32_t mask);

/**
 * Set a single host event.
 *
 * @param event         Event to set (EC_HOST_EVENT_*).
 */
static inline void host_set_single_event(int event)
{
	host_set_events(EC_HOST_EVENT_MASK(event));
}

/**
 * Clear one or more host event bits.
 *
 * @param mask          Event bits to clear (use EC_HOST_EVENT_MASK()).
 *                      Write 1 to a bit to clear it.
 */
void host_clear_events(uint32_t mask);

/**
 * Return the raw event state.
 */
uint32_t host_get_events(void);

/**
 * Send a response to the relevent driver for transmission
 *
 * Once command processing is complete, this is used to send a response
 * back to the host.
 *
 * @param args	Contains response to send
 */
void host_send_response(struct host_cmd_handler_args *args);

/**
 * Called by host interface module when a command is received.
 */
void host_command_received(struct host_cmd_handler_args *args);

/**
 * Return the expected host packet size given its header.
 *
 * Also does some sanity checking on the host request.
 *
 * @param r		Host request header
 * @return The expected packet size, or 0 if error.
 */
int host_request_expected_size(const struct ec_host_request *r);

/**
 * Handle a received host packet.
 *
 * @param packet	Host packet args
 */
void host_packet_receive(struct host_packet *pkt);

/* Register a host command handler */
#ifdef HAS_TASK_HOSTCMD
#define DECLARE_HOST_COMMAND(command, routine, version_mask)		\
	const struct host_command __keep __host_cmd_##command		\
	__attribute__((section(".rodata.hcmds")))			\
	     = {routine, command, version_mask}
#else
#define DECLARE_HOST_COMMAND(command, routine, version_mask)		\
	int (routine)(struct host_cmd_handler_args *args)		\
	__attribute__((unused))
#endif


/**
 * Politely ask the CPU to enable/disable its own throttling.
 *
 * @param throttle	Enable (!=0) or disable(0) throttling
 */
void host_throttle_cpu(int throttle);


/**
 * Signal host command task to send status to PD MCU.
 *
 * @new_chg_state PD MCU charge state
 */
void host_command_pd_send_status(enum pd_charge_state new_chg_state);

/**
 * Signal host command task to inform PD MCU that the EC is going to hibernate,
 * which will normally cause the PD MCU to hibernate also.
 */
void host_command_pd_request_hibernate(void);

/**
 * Get the active charge port from the PD
 *
 * @return -1 == none/unknown, 0 == left, 1 == right.
 */
int pd_get_active_charge_port(void);

/**
 * Send host command to PD MCU.
 *
 * @param command Host command number
 * @param version Version of host command
 * @param outdata Pointer to buffer of out data
 * @param outsize Size of buffer to out data
 * @param indata Pointer to buffer to store response
 * @param insize Size of buffer to store response
 */
int pd_host_command(int command, int version,
		    const void *outdata, int outsize,
		    void *indata, int insize);


/**
 * EC: Get verify boot mode
 * @return vboot_mode as the following:
 *    VBOOT_MODE_NORMAL    - normal mode
 *    VBOOT_MODE_DEVELOPER - developer mode
 *    VBOOT_MODE_RECOVERY  - recovery mode
 */
int host_get_vboot_mode(void);

#endif  /* __CROS_EC_HOST_COMMAND_H */