4
* Shared Memory Transport module
6
* Copyright (C) 2009 Texas Instruments, Inc.
8
* This package is free software; you can redistribute it and/or modify
9
* it under the terms of the GNU General Public License version 2 as
10
* published by the Free Software Foundation.
12
* THIS PACKAGE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
13
* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
14
* WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
18
/* Standard headers */
19
#include <linux/types.h>
21
/* Utilities headers */
22
#include <linux/string.h>
23
#include <linux/slab.h>
26
#include <syslink/atomic_linux.h>
27
/* Module level headers */
28
#include <multiproc.h>
29
#include <sharedregion.h>
30
#include <nameserver.h>
31
#include <gatepeterson.h>
36
#include <transportshm.h>
38
/* =============================================================================
40
* =============================================================================
43
/* Indicates that the transport is up. */
44
#define TRANSPORTSHM_UP 0xBADC0FFE
46
/* transportshm Version. */
47
#define TRANSPORTSHM_VERSION 1
50
* @brief Macro to make a correct module magic number with refCount
52
#define TRANSPORTSHM_MAKE_MAGICSTAMP(x) \
53
((TRANSPORTSHM_MODULEID << 12u) | (x))
55
#define ROUND_UP(a, b) (((a) + ((b) - 1)) & (~((b) - 1)))
57
typedef void (*transportshm_err_fxn)(enum transportshm_reason reason,
62
/* =============================================================================
64
* =============================================================================
67
* Defines the transportshm state object, which contains all the
68
* module specific information.
70
struct transportshm_module_object {
72
/* Flag to indicate initialization state of transportshr */
73
struct transportshm_config cfg;
74
/* transportshm configuration structure */
75
struct transportshm_config def_cfg;
76
/* Default module configuration */
77
struct transportshm_params def_inst_params;
78
/* Default instance parameters */
80
/* Handle to the gate for local thread safety */
82
[MULTIPROC_MAXPROCESSORS][MESSAGEQ_NUM_PRIORITY_QUEUES];
83
/* Transport to be set in messageq_register_transport */
84
transportshm_err_fxn err_fxn;
90
* Structure of attributes in shared memory
92
struct transportshm_attrs {
93
VOLATILE u32 flag; /* flag */
94
VOLATILE u32 creator_proc_id; /* Creator processor ID */
95
VOLATILE u32 notify_event_id; /* Notify event number */
96
VOLATILE u16 priority; /* priority */
97
VOLATILE u32 *gatemp_addr; /* gatemp shared memory srptr */
101
* Structure defining config parameters for the MessageQ transport
104
struct transportshm_object {
105
VOLATILE struct transportshm_attrs *self;
106
/* Attributes for local processor in shared memory */
107
VOLATILE struct transportshm_attrs *other;
108
/* Attributes for remote processor in shared memory */
110
/* List for this processor */
112
/* List for remote processor */
116
/* Shared memory allocated */
118
/* Whether to cache calls */
120
/* Notify event to be used */
122
/* The shared region id */
126
/* Priority of messages supported by this transport */
128
/* Gate for critical regions */
129
struct transportshm_params params;
130
/* Instance specific parameters */
133
/* =============================================================================
135
* =============================================================================
138
* @var transportshm_state
140
* transportshm state object variable
142
static struct transportshm_module_object transportshm_state = {
144
.def_cfg.err_fxn = NULL,
145
.def_inst_params.gate = NULL,
146
.def_inst_params.shared_addr = NULL,
147
.def_inst_params.notify_event_id = (u32)(-1),
148
.def_inst_params.priority = MESSAGEQ_NORMALPRI
151
/* Pointer to module state */
152
static struct transportshm_module_object *transportshm_module =
155
/* =============================================================================
156
* Forward declarations of internal functions
157
* =============================================================================
159
/* Callback function registered with the Notify module. */
160
static void _transportshm_notify_fxn(u16 proc_id,
166
/* Function to create/open the handle. */
167
static int _transportshm_create(struct transportshm_object **handle_ptr,
169
const struct transportshm_params *params,
172
/* =============================================================================
173
* APIs called directly by applications
174
* =============================================================================
177
* ======== transportshm_get_config ========
179
* Get the default configuration for the transportshm
182
* This function can be called by the application to get their
183
* configuration parameter to transportshm_setup filled in
184
* by the transportshm module with the default parameters.
185
* If the user does not wish to make any change in the default
186
* parameters, this API is not required to be called.
188
void transportshm_get_config(struct transportshm_config *cfg)
190
if (WARN_ON(cfg == NULL))
193
if (atomic_cmpmask_and_lt(&(transportshm_module->ref_count),
194
TRANSPORTSHM_MAKE_MAGICSTAMP(0),
195
TRANSPORTSHM_MAKE_MAGICSTAMP(1)) == true) {
196
memcpy(cfg, &(transportshm_module->def_cfg),
197
sizeof(struct transportshm_config));
199
memcpy(cfg, &(transportshm_module->cfg),
200
sizeof(struct transportshm_config));
205
pr_err("transportshm_get_config: Argument of type"
206
"(struct transportshm_config *) passed is null!\n");
211
* ======== transportshm_setup ========
213
* Setup the transportshm module.
215
* This function sets up the transportshm module. This
216
* function must be called before any other instance-level APIs can
218
* Module-level configuration needs to be provided to this
219
* function. If the user wishes to change some specific config
220
* parameters, then transportshm_getconfig can be called
221
* to get the configuration filled with the default values. After
222
* this, only the required configuration values can be changed. If
223
* the user does not wish to make any change in the default
224
* parameters, the application can simply call
225
* transportshm_setup with NULL parameters. The default
226
* parameters would get automatically used.
228
int transportshm_setup(const struct transportshm_config *cfg)
230
int status = TRANSPORTSHM_SUCCESS;
231
struct transportshm_config tmpCfg;
233
/* This sets the refCount variable is not initialized, upper 16 bits is
234
* written with module Id to ensure correctness of refCount variable.
236
atomic_cmpmask_and_set(&transportshm_module->ref_count,
237
TRANSPORTSHM_MAKE_MAGICSTAMP(0),
238
TRANSPORTSHM_MAKE_MAGICSTAMP(0));
240
if (atomic_inc_return(&transportshm_module->ref_count)
241
!= TRANSPORTSHM_MAKE_MAGICSTAMP(1u)) {
246
transportshm_get_config(&tmpCfg);
250
transportshm_module->gate_handle = \
251
kmalloc(sizeof(struct mutex), GFP_KERNEL);
252
if (transportshm_module->gate_handle == NULL) {
253
/* @retval TRANSPORTSHM_E_FAIL Failed to create
255
status = TRANSPORTSHM_E_FAIL;
256
pr_err("transportshm_setup: Failed to create mutex!\n");
257
atomic_set(&transportshm_module->ref_count,
258
TRANSPORTSHM_MAKE_MAGICSTAMP(0));
261
mutex_init(transportshm_module->gate_handle);
263
/* Copy the user provided values into the state object. */
264
memcpy(&transportshm_module->cfg, cfg,
265
sizeof(struct transportshm_config));
266
memset(&(transportshm_module->transports), 0, (sizeof(void *) * \
267
MULTIPROC_MAXPROCESSORS * MESSAGEQ_NUM_PRIORITY_QUEUES));
271
pr_err("transportshm_setup failed: status = 0x%x", status);
277
* ======== transportshm_destroy ========
279
* Destroy the transportshm module.
281
* Once this function is called, other transportshm module
282
* APIs, except for the transportshm_getConfig API cannot
285
int transportshm_destroy(void)
287
struct transportshm_object *obj = NULL;
292
if (WARN_ON(atomic_cmpmask_and_lt(
293
&(transportshm_module->ref_count),
294
TRANSPORTSHM_MAKE_MAGICSTAMP(0),
295
TRANSPORTSHM_MAKE_MAGICSTAMP(1)) == true)) {
300
if (!(atomic_dec_return(&transportshm_module->ref_count)
301
== TRANSPORTSHM_MAKE_MAGICSTAMP(0))) {
306
/* Temporarily increment ref_count here. */
307
atomic_set(&transportshm_module->ref_count,
308
TRANSPORTSHM_MAKE_MAGICSTAMP(1));
310
/* Delete any Transports that have not been deleted so far. */
311
for (i = 0; i < MULTIPROC_MAXPROCESSORS; i++) {
312
for (j = 0 ; j < MESSAGEQ_NUM_PRIORITY_QUEUES; j++) {
313
if (transportshm_module->transports[i][j] != \
315
obj = (struct transportshm_object *)
316
transportshm_module->transports[i][j];
317
if (obj->self != NULL) {
318
if (obj->self->creator_proc_id
321
&(transportshm_module->
325
&(transportshm_module->
332
/* Decrease the ref_count */
333
atomic_set(&transportshm_module->ref_count,
334
TRANSPORTSHM_MAKE_MAGICSTAMP(0));
336
if (transportshm_module->gate_handle != NULL) {
337
kfree(transportshm_module->gate_handle);
338
transportshm_module->gate_handle = NULL;
344
pr_err("transportshm_destroy failed: status = 0x%x\n", status);
350
* ======== transportshm_params_init ========
352
* Get Instance parameters
354
void transportshm_params_init(struct transportshm_params *params)
356
if (WARN_ON(atomic_cmpmask_and_lt(
357
&(transportshm_module->ref_count),
358
TRANSPORTSHM_MAKE_MAGICSTAMP(0),
359
TRANSPORTSHM_MAKE_MAGICSTAMP(1)) == true)) {
360
pr_err("transportshm_params_init: Module was "
361
" not initialized\n");
365
if (WARN_ON(params == NULL)) {
366
pr_err("transportshm_params_init: Argument of"
367
" type (struct transportshm_params *) "
372
memcpy(params, &(transportshm_module->def_inst_params),
373
sizeof(struct transportshm_params));
380
* ======== transportshm_create ========
382
* Create a transport instance. This function waits for the remote
383
* processor to complete its transport creation. Hence it must be
384
* called only after the remote processor is running.
386
void *transportshm_create(u16 proc_id,
387
const struct transportshm_params *params)
389
struct transportshm_object *handle = NULL;
392
BUG_ON(params == NULL);
393
BUG_ON(!(proc_id < multiproc_get_num_processors()));
394
if (WARN_ON(atomic_cmpmask_and_lt(
395
&(transportshm_module->ref_count),
396
TRANSPORTSHM_MAKE_MAGICSTAMP(0),
397
TRANSPORTSHM_MAKE_MAGICSTAMP(1)) == true)) {
402
if (WARN_ON(params == NULL)) {
406
if (transportshm_module->transports[proc_id][params->priority] \
408
/* Specified transport is already registered. */
409
status = MESSAGEQ_E_ALREADYEXISTS;
413
status = _transportshm_create(&handle, proc_id, params, true);
423
pr_err("transportshm_create failed: status = 0x%x\n", status);
429
* ======== transportshm_delete ========
433
int transportshm_delete(void **handle_ptr)
437
struct transportshm_object *handle;
441
if (WARN_ON(atomic_cmpmask_and_lt(
442
&(transportshm_module->ref_count),
443
TRANSPORTSHM_MAKE_MAGICSTAMP(0),
444
TRANSPORTSHM_MAKE_MAGICSTAMP(1)) == true)) {
448
if (WARN_ON(handle_ptr == NULL)) {
452
if (WARN_ON(*handle_ptr == NULL)) {
454
pr_warn("transportshm_delete: Invalid NULL"
455
" mqtshm_handle specified! status = 0x%x\n", status);
459
key = mutex_lock_interruptible(transportshm_state.gate_handle);
463
handle = (struct transportshm_object *) (*handle_ptr);
464
if (handle != NULL) {
465
if (handle->self != NULL) {
466
proc_id = handle->self->creator_proc_id;
467
/* Clear handle in the local array */
468
transportshm_module->
469
transports[proc_id][handle->priority] = NULL;
470
/* clear the self flag */
471
handle->self->flag = 0;
473
if (EXPECT_FALSE(handle->cache_enabled)) {
474
Cache_wbinv((Ptr)&(handle->self->flag),
475
sharedregion_get_cache_line_size(
483
if (handle->local_list != NULL) {
484
status = listmp_delete(&handle->local_list);
486
pr_warn("transportshm_delete: "
487
"Failed to delete local listmp "
491
if (handle->remote_list != NULL) {
492
tmp_status = listmp_close(&handle->remote_list);
493
if ((tmp_status < 0) && (status >= 0)) {
495
pr_warn("transportshm_delete: "
496
"Failed to close remote listmp "
501
messageq_unregister_transport(handle->
502
remote_proc_id, handle->params.priority);
504
tmp_status = notify_unregister_event_single(handle->
507
handle->notify_event_id);
508
if (tmp_status < 0) {
510
pr_warn("transportshm_delete: Failed to "
511
"unregister notify event!\n");
517
mutex_unlock(transportshm_state.gate_handle);
522
pr_err("transportshm_delete failed: "
523
"status = 0x%x\n", status);
528
* ========== transportshm_open_by_addr ===========
529
* Open a transport instance
532
transportshm_open_by_addr(void *shared_addr, void **handle_ptr)
535
struct transportshm_attrs *attrs = NULL;
536
struct transportshm_params params;
539
BUG_ON(shared_addr == NULL);
540
BUG_ON(handle_ptr == NULL);
542
if (WARN_ON(atomic_cmpmask_and_lt(
543
&(transportshm_module->ref_count),
544
TRANSPORTSHM_MAKE_MAGICSTAMP(0),
545
TRANSPORTSHM_MAKE_MAGICSTAMP(1)) == true)) {
550
if (shared_addr == NULL) {
555
if (handle_ptr == NULL) {
560
attrs = (struct transportshm_attrs *) shared_addr;
561
id = sharedregion_get_id(shared_addr);
563
if (id == SHAREDREGION_INVALIDREGIONID) {
567
if (((u32) shared_addr % sharedregion_get_cache_line_size(id) != 0)) {
573
/* invalidate the attrs before using it */
574
if (EXPECT_FALSE(SharedRegion_isCacheEnabled(id))) {
575
Cache_inv((Ptr) attrs,
576
sizeof(struct transportshm_attrs),
581
transportshm_params_init(¶ms);
582
/* set params field */
583
params.shared_addr = shared_addr;
584
params.notify_event_id = attrs->notify_event_id | \
585
(NOTIFY_SYSTEMKEY << 16);
586
params.priority = attrs->priority;
588
if (unlikely(attrs->flag != TRANSPORTSHM_UP)) {
594
/* Create the object */
595
status = _transportshm_create((struct transportshm_object **)
597
attrs->creator_proc_id, ¶ms, false);
604
pr_err("transportshm_open_by_addr failed: status = 0x%x\n", status);
609
* ========== transportshm_close ===========
610
* Close an opened transport instance
613
transportshm_close(void **handle_ptr)
617
struct transportshm_object *obj;
619
if (WARN_ON(atomic_cmpmask_and_lt(
620
&(transportshm_module->ref_count),
621
TRANSPORTSHM_MAKE_MAGICSTAMP(0),
622
TRANSPORTSHM_MAKE_MAGICSTAMP(1)) == true)) {
626
if (WARN_ON(handle_ptr == NULL)) {
630
if (WARN_ON(*handle_ptr == NULL)) {
635
obj = (struct transportshm_object *)(*handle_ptr);
636
transportshm_module->transports[obj->remote_proc_id]
637
[obj->params.priority] = NULL;
639
if (obj->other != NULL) {
640
/* other flag was set by remote proc */
641
obj->other->flag = 0;
643
if (EXPECT_FALSE(obj->cache_enabled)) {
644
Cache_wbInv(&(obj->other->flag),
645
sharedregion_get_cache_line_size
653
if (obj->gate != NULL) {
654
status = gatemp_close(&obj->gate);
656
status = TRANSPORTSHM_E_FAIL;
657
pr_err("transportshm_close: "
658
"gatemp_close failed, status [0x%x]\n",
663
if (obj->local_list != NULL) {
664
tmp_status = listmp_close(&obj->local_list);
665
if ((tmp_status < 0) && (status >= 0)) {
666
status = TRANSPORTSHM_E_FAIL;
667
pr_err("transportshm_close: "
668
"listmp_close(local_list) failed, "
669
"status [0x%x]\n", status);
673
if (obj->remote_list != NULL) {
674
tmp_status = listmp_close(&obj->remote_list);
675
if ((tmp_status < 0) && (status >= 0)) {
676
status = TRANSPORTSHM_E_FAIL;
677
pr_err("transportshm_close: "
678
"listmp_close(remote_list) failed, "
679
"status [0x%x]\n", status);
683
messageq_unregister_transport(obj->remote_proc_id,
684
obj->params.priority);
686
tmp_status = notify_unregister_event_single(obj->remote_proc_id, 0,
687
(obj->notify_event_id | (NOTIFY_SYSTEMKEY << 16)));
688
if ((tmp_status < 0) && (status >= 0))
689
status = TRANSPORTSHM_E_FAIL;
695
pr_err("transportshm_close failed: status = 0x%x\n", status);
701
* ======== transportshm_put ========
703
* Put msg to remote list
705
int transportshm_put(void *handle, void *msg)
708
struct transportshm_object *obj = NULL;
711
if (WARN_ON(atomic_cmpmask_and_lt(
712
&(transportshm_module->ref_count),
713
TRANSPORTSHM_MAKE_MAGICSTAMP(0),
714
TRANSPORTSHM_MAKE_MAGICSTAMP(1)) == true)) {
718
if (WARN_ON(handle == NULL)) {
722
if (WARN_ON(msg == NULL)) {
727
obj = (struct transportshm_object *)handle;
729
/* writeback invalidate the message */
730
if (EXPECT_FALSE(obj->cache_enabled)) {
731
Cache_wbinv((Ptr) msg,
732
((MessageQ_Msg)(msg))->msgSize,
737
/* make sure ListMP_put and sendEvent are done before remote executes */
738
/*key = gatemp_enter(obj->gate);*/
739
status = listmp_put_tail(obj->remote_list, (struct listmp_elem *) msg);
741
pr_err("transportshm_put: Failed to put "
742
"message in the shared list! status = 0x%x\n", status);
746
status = notify_send_event(obj->remote_proc_id, 0,
747
obj->notify_event_id, 0, false);
749
goto notify_send_fail;
755
pr_err("transportshm_put: Notification to remote "
756
"processor failed, status = 0x%x\n", status);
757
/* If sending the event failed, then remove the element from the */
758
/* list. Ignore the status of remove. */
759
listmp_remove(obj->remote_list, (struct listmp_elem *) msg);
762
/*gatemp_leave(obj->gate, key);*/
765
pr_err("transportshm_put failed: status = 0x%x\n", status);
770
* ======== transportshm_control ========
774
int transportshm_control(void *handle, u32 cmd, u32 *cmd_arg)
776
BUG_ON(handle == NULL);
778
pr_err("transportshm_control not supported!\n");
779
return TRANSPORTSHM_E_NOTSUPPORTED;
783
* ======== transportshm_get_status ========
787
enum transportshm_status transportshm_get_status(void *handle)
789
struct transportshm_object *obj = \
790
(struct transportshm_object *) handle;
798
* ======== transportshm_put ========
800
* Get shared memory requirements.
802
u32 transportshm_shared_mem_req(const struct transportshm_params *params)
807
struct listmp_params list_params;
810
if (params == NULL) {
814
region_id = sharedregion_get_id(params->shared_addr);
816
if (region_id == SHAREDREGION_INVALIDREGIONID) {
821
min_align = 4; /*memory_get_max_default_type_align(); */
822
if (sharedregion_get_cache_line_size(region_id) > min_align)
823
min_align = sharedregion_get_cache_line_size(region_id);
825
/* for the Attrs structure */
826
mem_req = ROUND_UP(sizeof(struct transportshm_attrs), min_align);
828
/* for the second Attrs structure */
829
mem_req += ROUND_UP(sizeof(struct transportshm_attrs), min_align);
831
listmp_params_init(&list_params);
832
list_params.region_id = region_id;
833
/* for local listMP */
834
mem_req += listmp_shared_mem_req(&list_params);
836
/* for remote listMP */
837
mem_req += listmp_shared_mem_req(&list_params);
841
pr_err("transportshm_shared_mem_req failed: "
842
"status = 0x%x\n", status);
848
/* =============================================================================
850
* =============================================================================
853
* ======== _transportshm_notify_fxn ========
855
* Callback function registered with the Notify module.
857
static void _transportshm_notify_fxn(u16 proc_id, u16 line_id, u32 event_no,
858
uint *arg, u32 payload)
860
struct transportshm_object *obj = NULL;
861
messageq_msg msg = NULL;
865
key = mutex_lock_interruptible(transportshm_state.gate_handle);
870
if (WARN_ON(arg == NULL))
873
obj = (struct transportshm_object *)arg;
874
/* While there is are messages, get them out and send them to
875
* their final destination. */
877
msg = (messageq_msg) listmp_get_head(obj->local_list);
880
while (msg != NULL) {
881
/* Get the destination message queue Id */
882
queue_id = messageq_get_dst_queue(msg);
884
/* put the message to the destination queue */
885
messageq_put(queue_id, msg);
888
listmp_get_head(obj->local_list);
892
mutex_unlock(transportshm_state.gate_handle);
896
mutex_unlock(transportshm_state.gate_handle);
898
pr_err("transportshm_notify_fxn: argument passed is NULL!\n");
904
* ======== transportshm_delete ========
906
* This will set the asynchronous error function for the transport module
908
void transportshm_set_err_fxn( void (*err_fxn)(
909
enum transportshm_reason reason,
916
key = mutex_lock_interruptible(transportshm_module->gate_handle);
920
transportshm_module->cfg.err_fxn = err_fxn;
921
mutex_unlock(transportshm_module->gate_handle);
929
* ========= _transportshm_create =========
931
* Internal function for create()/open()
933
static int _transportshm_create(struct transportshm_object **handle_ptr,
934
u16 proc_id, const struct transportshm_params *params,
938
struct transportshm_object *handle = NULL;
939
void *local_addr = NULL;
943
struct listmp_params listmp_params[2];
945
BUG_ON(handle_ptr == NULL);
946
BUG_ON(params == NULL);
947
BUG_ON(proc_id >= multiproc_get_num_processors());
950
* Determine who gets the '0' slot and who gets the '1' slot
951
* The '0' slot is given to the lower multiproc id.
953
if (multiproc_self() < proc_id) {
961
handle = kzalloc(sizeof(struct transportshm_object), GFP_KERNEL);
962
if (handle == NULL) {
966
*handle_ptr = handle;
968
if (create_flag == false) {
969
/* Open by shared addr */
970
handle->self = (struct transportshm_attrs *)
972
handle->region_id = sharedregion_get_id(params->shared_addr);
973
BUG_ON(handle->region_id == SHAREDREGION_INVALIDREGIONID);
975
handle->cache_enabled = sharedregion_is_cache_enabled(handle->
978
local_addr = sharedregion_get_ptr((u32 *)handle->self->
980
BUG_ON(local_addr == NULL);
982
status = gatemp_open_by_addr(local_addr, &handle->gate);
988
/* Init the gate for ListMP create below */
989
if (params->gate != NULL)
990
handle->gate = params->gate;
992
handle->gate = gatemp_get_default_remote();
994
if (handle->gate == NULL) {
998
memcpy(&(handle->params), params,
999
sizeof(struct transportshm_params));
1000
handle->region_id = sharedregion_get_id(params->shared_addr);
1002
/* Assert that the buffer is in a valid shared
1005
if (handle->region_id == SHAREDREGION_INVALIDREGIONID) {
1009
if (((u32)params->shared_addr
1010
% sharedregion_get_cache_line_size(handle->region_id)
1016
/* set handle's cache_enabled, type, attrs */
1017
handle->cache_enabled = sharedregion_is_cache_enabled(
1019
handle->self = (struct transportshm_attrs *)
1020
params->shared_addr;
1023
/* Determine the minimum alignment to align to */
1024
min_align = 4; /*memory_get_max_default_type_align(); */
1025
if (sharedregion_get_cache_line_size(handle->region_id) > min_align)
1026
min_align = sharedregion_get_cache_line_size(handle->
1029
* Carve up the shared memory.
1030
* If cache is enabled, these need to be on separate cache
1031
* lines. This is done with min_align and ROUND_UP function.
1034
handle->other = (struct transportshm_attrs *)(((u32)handle->self) +
1035
(ROUND_UP(sizeof(struct transportshm_attrs), min_align)));
1038
listmp_params_init(&(listmp_params[0]));
1039
listmp_params[0].gatemp_handle = handle->gate;
1040
listmp_params[0].shared_addr = (void *)(((u32)handle->other)
1041
+ (ROUND_UP(sizeof(struct transportshm_attrs), min_align)));
1043
listmp_params_init(&listmp_params[1]);
1044
listmp_params[1].gatemp_handle = handle->gate;
1045
listmp_params[1].shared_addr = (void *)
1046
(((u32)listmp_params[0].shared_addr)
1047
+ listmp_shared_mem_req(&listmp_params[0]));
1049
handle->notify_event_id = params->notify_event_id;
1050
handle->priority = params->priority;
1051
handle->remote_proc_id = proc_id;
1053
if (create_flag == true) {
1054
handle->local_list =
1055
listmp_create(&(listmp_params[local_index]));
1056
if (handle->local_list == NULL) {
1060
handle->remote_list = listmp_create(
1061
&(listmp_params[remote_index]));
1062
if (handle->remote_list == NULL) {
1067
/* Open the local ListMP instance */
1068
status = listmp_open_by_addr(
1069
listmp_params[local_index].shared_addr,
1070
&(handle->local_list));
1076
status = listmp_open_by_addr(
1077
listmp_params[remote_index].shared_addr,
1078
&(handle->remote_list));
1085
status = notify_register_event_single(proc_id,
1087
params->notify_event_id,
1088
_transportshm_notify_fxn,
1095
if (create_flag == true) {
1096
handle->self->creator_proc_id = multiproc_self();
1097
handle->self->notify_event_id = handle->notify_event_id;
1098
handle->self->priority = handle->priority;
1100
/* Store the GateMP shared_addr in the Attrs */
1101
handle->self->gatemp_addr =
1102
gatemp_get_shared_addr(handle->gate);
1103
handle->self->flag = TRANSPORTSHM_UP;
1105
if (EXPECT_FALSE(handle->cache_enabled)) {
1106
Cache_wbinv((Ptr) handle->self,
1107
sizeof(struct transportshm_attrs),
1113
handle->other->flag = TRANSPORTSHM_UP;
1115
if (EXPECT_FALSE(handle->cache_enabled)) {
1116
Cache_wb((Ptr)&(handle->other->flag),
1124
/* Register the transport with MessageQ */
1125
status = messageq_register_transport(handle, proc_id,
1131
handle->status = TRANSPORTSHM_UP;
1132
/* Set handle in the local array. */
1133
transportshm_module->transports[handle->remote_proc_id]
1134
[handle->params.priority] = handle;
1139
/* Cleanup in case of error. */
1140
if (create_flag == true)
1141
transportshm_delete((void **)handle_ptr);
1143
transportshm_close((void **)handle_ptr);