Linux Kernel  3.7.1
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Groups Pages
hsi.h
Go to the documentation of this file.
1 /*
2  * HSI core header file.
3  *
4  * Copyright (C) 2010 Nokia Corporation. All rights reserved.
5  *
6  * Contact: Carlos Chinea <[email protected]>
7  *
8  * This program is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU General Public License
10  * version 2 as published by the Free Software Foundation.
11  *
12  * This program is distributed in the hope that it will be useful, but
13  * WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15  * General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program; if not, write to the Free Software
19  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
20  * 02110-1301 USA
21  */
22 
23 #ifndef __LINUX_HSI_H__
24 #define __LINUX_HSI_H__
25 
26 #include <linux/device.h>
27 #include <linux/mutex.h>
28 #include <linux/scatterlist.h>
29 #include <linux/list.h>
30 #include <linux/module.h>
31 #include <linux/notifier.h>
32 
33 /* HSI message ttype */
34 #define HSI_MSG_READ 0
35 #define HSI_MSG_WRITE 1
36 
37 /* HSI configuration values */
38 enum {
41 };
42 
43 enum {
44  HSI_FLOW_SYNC, /* Synchronized flow */
45  HSI_FLOW_PIPE, /* Pipelined flow */
46 };
47 
48 enum {
49  HSI_ARB_RR, /* Round-robin arbitration */
50  HSI_ARB_PRIO, /* Channel priority arbitration */
51 };
52 
53 #define HSI_MAX_CHANNELS 16
54 
55 /* HSI message status codes */
56 enum {
57  HSI_STATUS_COMPLETED, /* Message transfer is completed */
58  HSI_STATUS_PENDING, /* Message pending to be read/write (POLL) */
59  HSI_STATUS_PROCEEDING, /* Message transfer is ongoing */
60  HSI_STATUS_QUEUED, /* Message waiting to be served */
61  HSI_STATUS_ERROR, /* Error when message transfer was ongoing */
62 };
63 
64 /* HSI port event codes */
65 enum {
68 };
69 
78 struct hsi_config {
79  unsigned int mode;
80  unsigned int channels;
81  unsigned int speed;
82  union {
83  unsigned int flow; /* RX only */
84  unsigned int arb_mode; /* TX only */
85  };
86 };
87 
99  const char *name;
100  unsigned int hsi_id;
101  unsigned int port;
106 };
107 
108 #ifdef CONFIG_HSI_BOARDINFO
109 extern int hsi_register_board_info(struct hsi_board_info const *info,
110  unsigned int len);
111 #else
112 static inline int hsi_register_board_info(struct hsi_board_info const *info,
113  unsigned int len)
114 {
115  return 0;
116 }
117 #endif /* CONFIG_HSI_BOARDINFO */
118 
128 struct hsi_client {
129  struct device device;
132  /* private: */
133  void (*ehandler)(struct hsi_client *, unsigned long);
134  unsigned int pclaimed:1;
136 };
137 
138 #define to_hsi_client(dev) container_of(dev, struct hsi_client, device)
139 
140 static inline void hsi_client_set_drvdata(struct hsi_client *cl, void *data)
141 {
142  dev_set_drvdata(&cl->device, data);
143 }
144 
145 static inline void *hsi_client_drvdata(struct hsi_client *cl)
146 {
147  return dev_get_drvdata(&cl->device);
148 }
149 
151  void (*handler)(struct hsi_client *, unsigned long));
152 int hsi_unregister_port_event(struct hsi_client *cl);
153 
160 };
161 
162 #define to_hsi_client_driver(drv) container_of(drv, struct hsi_client_driver,\
163  driver)
164 
166 
167 static inline void hsi_unregister_client_driver(struct hsi_client_driver *drv)
168 {
169  driver_unregister(&drv->driver);
170 }
171 
187 struct hsi_msg {
188  struct list_head link;
189  struct hsi_client *cl;
190  struct sg_table sgt;
191  void *context;
192 
193  void (*complete)(struct hsi_msg *msg);
194  void (*destructor)(struct hsi_msg *msg);
195 
196  int status;
197  unsigned int actual_len;
198  unsigned int channel;
199  unsigned int ttype:1;
200  unsigned int break_frame:1;
201 };
202 
203 struct hsi_msg *hsi_alloc_msg(unsigned int n_frag, gfp_t flags);
204 void hsi_free_msg(struct hsi_msg *msg);
205 
223 struct hsi_port {
224  struct device device;
227  unsigned int num;
228  unsigned int shared:1;
229  int claimed;
230  struct mutex lock;
231  int (*async)(struct hsi_msg *msg);
232  int (*setup)(struct hsi_client *cl);
233  int (*flush)(struct hsi_client *cl);
234  int (*start_tx)(struct hsi_client *cl);
235  int (*stop_tx)(struct hsi_client *cl);
236  int (*release)(struct hsi_client *cl);
237  /* private */
239 };
240 
241 #define to_hsi_port(dev) container_of(dev, struct hsi_port, device)
242 #define hsi_get_port(cl) to_hsi_port((cl)->device.parent)
243 
244 int hsi_event(struct hsi_port *port, unsigned long event);
245 int hsi_claim_port(struct hsi_client *cl, unsigned int share);
246 void hsi_release_port(struct hsi_client *cl);
247 
248 static inline int hsi_port_claimed(struct hsi_client *cl)
249 {
250  return cl->pclaimed;
251 }
252 
253 static inline void hsi_port_set_drvdata(struct hsi_port *port, void *data)
254 {
255  dev_set_drvdata(&port->device, data);
256 }
257 
258 static inline void *hsi_port_drvdata(struct hsi_port *port)
259 {
260  return dev_get_drvdata(&port->device);
261 }
262 
272  struct device device;
273  struct module *owner;
274  unsigned int id;
275  unsigned int num_ports;
276  struct hsi_port **port;
277 };
278 
279 #define to_hsi_controller(dev) container_of(dev, struct hsi_controller, device)
280 
281 struct hsi_controller *hsi_alloc_controller(unsigned int n_ports, gfp_t flags);
282 void hsi_put_controller(struct hsi_controller *hsi);
283 int hsi_register_controller(struct hsi_controller *hsi);
284 void hsi_unregister_controller(struct hsi_controller *hsi);
285 
286 static inline void hsi_controller_set_drvdata(struct hsi_controller *hsi,
287  void *data)
288 {
289  dev_set_drvdata(&hsi->device, data);
290 }
291 
292 static inline void *hsi_controller_drvdata(struct hsi_controller *hsi)
293 {
294  return dev_get_drvdata(&hsi->device);
295 }
296 
297 static inline struct hsi_port *hsi_find_port_num(struct hsi_controller *hsi,
298  unsigned int num)
299 {
300  return (num < hsi->num_ports) ? hsi->port[num] : NULL;
301 }
302 
303 /*
304  * API for HSI clients
305  */
306 int hsi_async(struct hsi_client *cl, struct hsi_msg *msg);
307 
314 static inline unsigned int hsi_id(struct hsi_client *cl)
315 {
316  return to_hsi_controller(cl->device.parent->parent)->id;
317 }
318 
325 static inline unsigned int hsi_port_id(struct hsi_client *cl)
326 {
327  return to_hsi_port(cl->device.parent)->num;
328 }
329 
339 static inline int hsi_setup(struct hsi_client *cl)
340 {
341  if (!hsi_port_claimed(cl))
342  return -EACCES;
343  return hsi_get_port(cl)->setup(cl);
344 }
345 
355 static inline int hsi_flush(struct hsi_client *cl)
356 {
357  if (!hsi_port_claimed(cl))
358  return -EACCES;
359  return hsi_get_port(cl)->flush(cl);
360 }
361 
369 static inline int hsi_async_read(struct hsi_client *cl, struct hsi_msg *msg)
370 {
371  msg->ttype = HSI_MSG_READ;
372  return hsi_async(cl, msg);
373 }
374 
382 static inline int hsi_async_write(struct hsi_client *cl, struct hsi_msg *msg)
383 {
384  msg->ttype = HSI_MSG_WRITE;
385  return hsi_async(cl, msg);
386 }
387 
394 static inline int hsi_start_tx(struct hsi_client *cl)
395 {
396  if (!hsi_port_claimed(cl))
397  return -EACCES;
398  return hsi_get_port(cl)->start_tx(cl);
399 }
400 
407 static inline int hsi_stop_tx(struct hsi_client *cl)
408 {
409  if (!hsi_port_claimed(cl))
410  return -EACCES;
411  return hsi_get_port(cl)->stop_tx(cl);
412 }
413 #endif /* __LINUX_HSI_H__ */