1/*  *********************************************************************
2    *  Broadcom Common Firmware Environment (CFE)
3    *
4    *  IOCB dispatcher		    	File: cfe_vendor_xreq.c
5    *
6    *  This routine is the main API dispatch for CFE.  User API
7    *  calls, via the ROM entry point, get dispatched to routines
8    *  in this module.
9    *
10    *  This version of cfe_xreq is used for vendor extensions to
11    *  CFE.
12    *
13    *  This module looks similar to cfe_iocb_dispatch - it is different
14    *  in that the data structure used, cfe_xiocb_t, uses fixed
15    *  size field members (specifically, all 64-bits) no matter how
16    *  the firmware is compiled.  This ensures a consistent API
17    *  interface on any implementation.  When you call CFE
18    *  from another program, the entry vector comes here first.
19    *
20    *  Should the normal cfe_iocb interface change, this one should
21    *  be kept the same for backward compatibility reasons.
22    *
23    *  Author:  Mitch Lichtenberg
24    *
25    *********************************************************************
26    *
27    *  Copyright 2000,2001,2002,2003
28    *  Broadcom Corporation. All rights reserved.
29    *
30    *  This software is furnished under license and may be used and
31    *  copied only in accordance with the following terms and
32    *  conditions.  Subject to these conditions, you may download,
33    *  copy, install, use, modify and distribute modified or unmodified
34    *  copies of this software in source and/or binary form.  No title
35    *  or ownership is transferred hereby.
36    *
37    *  1) Any source code used, modified or distributed must reproduce
38    *     and retain this copyright notice and list of conditions
39    *     as they appear in the source file.
40    *
41    *  2) No right is granted to use any trade name, trademark, or
42    *     logo of Broadcom Corporation.  The "Broadcom Corporation"
43    *     name may not be used to endorse or promote products derived
44    *     from this software without the prior written permission of
45    *     Broadcom Corporation.
46    *
47    *  3) THIS SOFTWARE IS PROVIDED "AS-IS" AND ANY EXPRESS OR
48    *     IMPLIED WARRANTIES, INCLUDING BUT NOT LIMITED TO, ANY IMPLIED
49    *     WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
50    *     PURPOSE, OR NON-INFRINGEMENT ARE DISCLAIMED. IN NO EVENT
51    *     SHALL BROADCOM BE LIABLE FOR ANY DAMAGES WHATSOEVER, AND IN
52    *     PARTICULAR, BROADCOM SHALL NOT BE LIABLE FOR DIRECT, INDIRECT,
53    *     INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
54    *     (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
55    *     GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
56    *     BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
57    *     OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
58    *     TORT (INCLUDING NEGLIGENCE OR OTHERWISE), EVEN IF ADVISED OF
59    *     THE POSSIBILITY OF SUCH DAMAGE.
60    ********************************************************************* */
61
62
63#include "cfe.h"
64#include "cfe_vendor_iocb.h"
65#include "cfe_xiocb.h"
66#include "cfe_vendor_xiocb.h"
67#include "cfe_mem.h"
68#include "env_subr.h"
69
70
71/*  *********************************************************************
72    *  Constants
73    ********************************************************************* */
74
75/* enum values for various plist types */
76
77#define PLBUF	1		/* iocb_buffer_t */
78
79/*  *********************************************************************
80    *  Structures
81    ********************************************************************* */
82
83struct cfe_vendor_xcmd_dispatch_s {
84    int xplistsize;
85    int iplistsize;
86    int plisttype;
87};
88
89
90/*  *********************************************************************
91    *  Command conversion table
92    *  This table contains useful information for converting
93    *  iocbs to xiocbs.
94    ********************************************************************* */
95
96const static struct cfe_vendor_xcmd_dispatch_s
97   cfe_vendor_xcmd_dispatch_table[CFE_CMD_VENDOR_MAX-CFE_CMD_VENDOR_USE] = {
98    {sizeof(xiocb_buffer_t), sizeof(iocb_buffer_t), PLBUF},	/* 0 : CFE_CMD_VENDOR_SAMPLE */
99};
100
101
102/*  *********************************************************************
103    *  Externs
104    ********************************************************************* */
105
106extern int cfe_vendor_iocb_dispatch(cfe_vendor_iocb_t *iocb);
107extern cfe_int_t cfe_vendor_doxreq(cfe_vendor_xiocb_t *xiocb);
108
109/*  *********************************************************************
110    *  cfe_vendor_doxreq(xiocb)
111    *
112    *  Process an xiocb request.  This routine converts an xiocb
113    *  into an iocb, calls the IOCB dispatcher, converts the results
114    *  back into the xiocb, and returns.
115    *
116    *  Input parameters:
117    *  	   xiocb - pointer to user xiocb
118    *
119    *  Return value:
120    *  	   command status, <0 if error occured
121    ********************************************************************* */
122
123cfe_int_t cfe_vendor_doxreq(cfe_vendor_xiocb_t *xiocb)
124{
125    const struct cfe_vendor_xcmd_dispatch_s *disp;
126    cfe_vendor_iocb_t iiocb;
127    cfe_int_t res;
128
129    /*
130     * Check for commands codes out of range
131     */
132
133    if ((xiocb->xiocb_fcode < CFE_CMD_VENDOR_USE) ||
134	(xiocb->xiocb_fcode >= CFE_CMD_VENDOR_MAX)) {
135	xiocb->xiocb_status = CFE_ERR_INV_COMMAND;
136	return xiocb->xiocb_status;
137	}
138
139    /*
140     * Check for command codes in range but invalid
141     */
142
143    disp = &cfe_vendor_xcmd_dispatch_table[xiocb->xiocb_fcode - CFE_CMD_VENDOR_USE];
144
145    if (disp->xplistsize < 0) {
146	xiocb->xiocb_status = CFE_ERR_INV_COMMAND;
147	return xiocb->xiocb_status;
148	}
149
150    /*
151     * Check for invalid parameter list size
152     */
153
154    if (disp->xplistsize != xiocb->xiocb_psize) {
155	xiocb->xiocb_status = CFE_ERR_INV_PARAM;
156	return xiocb->xiocb_status;
157	}
158
159    /*
160     * Okay, copy parameters into the internal IOCB.
161     * First, the fixed header.
162     */
163
164    iiocb.iocb_fcode = (unsigned int) xiocb->xiocb_fcode;
165    iiocb.iocb_status = (int) xiocb->xiocb_status;
166    iiocb.iocb_handle = (int) xiocb->xiocb_handle;
167    iiocb.iocb_flags = (unsigned int) xiocb->xiocb_flags;
168    iiocb.iocb_psize = (unsigned int) disp->iplistsize;
169
170    /*
171     * Now the parameter list
172     */
173
174    switch (disp->plisttype) {
175	case PLBUF:
176	    iiocb.plist.iocb_buffer.buf_offset = (cfe_offset_t) xiocb->plist.xiocb_buffer.buf_offset;
177	    iiocb.plist.iocb_buffer.buf_ptr = xiocb->plist.xiocb_buffer.buf_ptr;
178	    iiocb.plist.iocb_buffer.buf_length = (unsigned int) xiocb->plist.xiocb_buffer.buf_length;
179	    iiocb.plist.iocb_buffer.buf_retlen = (unsigned int) xiocb->plist.xiocb_buffer.buf_retlen;
180	    iiocb.plist.iocb_buffer.buf_ioctlcmd = (unsigned int) xiocb->plist.xiocb_buffer.buf_ioctlcmd;
181	    break;
182	}
183
184    /*
185     * Do the internal function dispatch
186     */
187
188    res = (cfe_int_t) cfe_vendor_iocb_dispatch(&iiocb);
189
190    /*
191     * Now convert the parameter list members back
192     */
193
194    switch (disp->plisttype) {
195	case PLBUF:
196	    xiocb->plist.xiocb_buffer.buf_offset = (cfe_uint_t) iiocb.plist.iocb_buffer.buf_offset;
197	    xiocb->plist.xiocb_buffer.buf_ptr = (cfe_xptr_t) (uintptr_t) iiocb.plist.iocb_buffer.buf_ptr;
198	    xiocb->plist.xiocb_buffer.buf_length = (cfe_uint_t) iiocb.plist.iocb_buffer.buf_length;
199	    xiocb->plist.xiocb_buffer.buf_retlen = (cfe_uint_t) iiocb.plist.iocb_buffer.buf_retlen;
200	    xiocb->plist.xiocb_buffer.buf_ioctlcmd = (cfe_uint_t) iiocb.plist.iocb_buffer.buf_ioctlcmd;
201	    break;
202	}
203
204    /*
205     * And the fixed header
206     */
207
208    xiocb->xiocb_status = (cfe_int_t) iiocb.iocb_status;
209    xiocb->xiocb_handle = (cfe_int_t) iiocb.iocb_handle;
210    xiocb->xiocb_flags = (cfe_uint_t) iiocb.iocb_flags;
211
212    return xiocb->xiocb_status;
213}
214