0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014 #define SOURCEFILE_NAME "hpicmn.c"
0015
0016 #include "hpi_internal.h"
0017 #include "hpidebug.h"
0018 #include "hpimsginit.h"
0019
0020 #include "hpicmn.h"
0021
0022 struct hpi_adapters_list {
0023 struct hpios_spinlock list_lock;
0024 struct hpi_adapter_obj adapter[HPI_MAX_ADAPTERS];
0025 u16 gw_num_adapters;
0026 };
0027
0028 static struct hpi_adapters_list adapters;
0029
0030
0031
0032
0033
0034
0035
0036
0037 u16 hpi_validate_response(struct hpi_message *phm, struct hpi_response *phr)
0038 {
0039 if (phr->type != HPI_TYPE_RESPONSE) {
0040 HPI_DEBUG_LOG(ERROR, "header type %d invalid\n", phr->type);
0041 return HPI_ERROR_INVALID_RESPONSE;
0042 }
0043
0044 if (phr->object != phm->object) {
0045 HPI_DEBUG_LOG(ERROR, "header object %d invalid\n",
0046 phr->object);
0047 return HPI_ERROR_INVALID_RESPONSE;
0048 }
0049
0050 if (phr->function != phm->function) {
0051 HPI_DEBUG_LOG(ERROR, "header function %d invalid\n",
0052 phr->function);
0053 return HPI_ERROR_INVALID_RESPONSE;
0054 }
0055
0056 return 0;
0057 }
0058
0059 u16 hpi_add_adapter(struct hpi_adapter_obj *pao)
0060 {
0061 u16 retval = 0;
0062
0063
0064 hpios_alistlock_lock(&adapters);
0065
0066 if (pao->index >= HPI_MAX_ADAPTERS) {
0067 retval = HPI_ERROR_BAD_ADAPTER_NUMBER;
0068 goto unlock;
0069 }
0070
0071 if (adapters.adapter[pao->index].type) {
0072 int a;
0073 for (a = HPI_MAX_ADAPTERS - 1; a >= 0; a--) {
0074 if (!adapters.adapter[a].type) {
0075 HPI_DEBUG_LOG(WARNING,
0076 "ASI%X duplicate index %d moved to %d\n",
0077 pao->type, pao->index, a);
0078 pao->index = a;
0079 break;
0080 }
0081 }
0082 if (a < 0) {
0083 retval = HPI_ERROR_DUPLICATE_ADAPTER_NUMBER;
0084 goto unlock;
0085 }
0086 }
0087 adapters.adapter[pao->index] = *pao;
0088 hpios_dsplock_init(&adapters.adapter[pao->index]);
0089 adapters.gw_num_adapters++;
0090
0091 unlock:
0092 hpios_alistlock_unlock(&adapters);
0093 return retval;
0094 }
0095
0096 void hpi_delete_adapter(struct hpi_adapter_obj *pao)
0097 {
0098 if (!pao->type) {
0099 HPI_DEBUG_LOG(ERROR, "removing null adapter?\n");
0100 return;
0101 }
0102
0103 hpios_alistlock_lock(&adapters);
0104 if (adapters.adapter[pao->index].type)
0105 adapters.gw_num_adapters--;
0106 memset(&adapters.adapter[pao->index], 0, sizeof(adapters.adapter[0]));
0107 hpios_alistlock_unlock(&adapters);
0108 }
0109
0110
0111
0112
0113
0114
0115
0116 struct hpi_adapter_obj *hpi_find_adapter(u16 adapter_index)
0117 {
0118 struct hpi_adapter_obj *pao = NULL;
0119
0120 if (adapter_index >= HPI_MAX_ADAPTERS) {
0121 HPI_DEBUG_LOG(VERBOSE, "find_adapter invalid index %d\n",
0122 adapter_index);
0123 return NULL;
0124 }
0125
0126 pao = &adapters.adapter[adapter_index];
0127 if (pao->type != 0) {
0128
0129
0130
0131
0132 return pao;
0133 } else {
0134
0135
0136
0137
0138 return NULL;
0139 }
0140 }
0141
0142
0143
0144
0145
0146 static void wipe_adapter_list(void)
0147 {
0148 memset(&adapters, 0, sizeof(adapters));
0149 }
0150
0151 static void subsys_get_adapter(struct hpi_message *phm,
0152 struct hpi_response *phr)
0153 {
0154 int count = phm->obj_index;
0155 u16 index = 0;
0156
0157
0158 for (index = 0; index < HPI_MAX_ADAPTERS; index++) {
0159 if (adapters.adapter[index].type) {
0160 if (!count)
0161 break;
0162 count--;
0163 }
0164 }
0165
0166 if (index < HPI_MAX_ADAPTERS) {
0167 phr->u.s.adapter_index = adapters.adapter[index].index;
0168 phr->u.s.adapter_type = adapters.adapter[index].type;
0169 } else {
0170 phr->u.s.adapter_index = 0;
0171 phr->u.s.adapter_type = 0;
0172 phr->error = HPI_ERROR_INVALID_OBJ_INDEX;
0173 }
0174 }
0175
0176 static unsigned int control_cache_alloc_check(struct hpi_control_cache *pC)
0177 {
0178 unsigned int i;
0179 int cached = 0;
0180 if (!pC)
0181 return 0;
0182
0183 if (pC->init)
0184 return pC->init;
0185
0186 if (!pC->p_cache)
0187 return 0;
0188
0189 if (pC->control_count && pC->cache_size_in_bytes) {
0190 char *p_master_cache;
0191 unsigned int byte_count = 0;
0192
0193 p_master_cache = (char *)pC->p_cache;
0194 HPI_DEBUG_LOG(DEBUG, "check %d controls\n",
0195 pC->control_count);
0196 for (i = 0; i < pC->control_count; i++) {
0197 struct hpi_control_cache_info *info =
0198 (struct hpi_control_cache_info *)
0199 &p_master_cache[byte_count];
0200 u16 control_index = info->control_index;
0201
0202 if (control_index >= pC->control_count) {
0203 HPI_DEBUG_LOG(INFO,
0204 "adap %d control index %d out of range, cache not ready?\n",
0205 pC->adap_idx, control_index);
0206 return 0;
0207 }
0208
0209 if (!info->size_in32bit_words) {
0210 if (!i) {
0211 HPI_DEBUG_LOG(INFO,
0212 "adap %d cache not ready?\n",
0213 pC->adap_idx);
0214 return 0;
0215 }
0216
0217
0218
0219
0220 HPI_DEBUG_LOG(ERROR,
0221 "adap %d zero size cache entry %d\n",
0222 pC->adap_idx, i);
0223 break;
0224 }
0225
0226 if (info->control_type) {
0227 pC->p_info[control_index] = info;
0228 cached++;
0229 } else {
0230 pC->p_info[control_index] = NULL;
0231 }
0232
0233 byte_count += info->size_in32bit_words * 4;
0234
0235 HPI_DEBUG_LOG(VERBOSE,
0236 "cached %d, pinfo %p index %d type %d size %d\n",
0237 cached, pC->p_info[info->control_index],
0238 info->control_index, info->control_type,
0239 info->size_in32bit_words);
0240
0241
0242
0243
0244
0245 if (byte_count >= pC->cache_size_in_bytes)
0246 break;
0247
0248 if (info->control_index == pC->control_count - 1)
0249 break;
0250 }
0251
0252 if (byte_count != pC->cache_size_in_bytes)
0253 HPI_DEBUG_LOG(WARNING,
0254 "adap %d bytecount %d != cache size %d\n",
0255 pC->adap_idx, byte_count,
0256 pC->cache_size_in_bytes);
0257 else
0258 HPI_DEBUG_LOG(DEBUG,
0259 "adap %d cache good, bytecount == cache size = %d\n",
0260 pC->adap_idx, byte_count);
0261
0262 pC->init = (u16)cached;
0263 }
0264 return pC->init;
0265 }
0266
0267
0268
0269 static short find_control(u16 control_index,
0270 struct hpi_control_cache *p_cache, struct hpi_control_cache_info **pI)
0271 {
0272 if (!control_cache_alloc_check(p_cache)) {
0273 HPI_DEBUG_LOG(VERBOSE,
0274 "control_cache_alloc_check() failed %d\n",
0275 control_index);
0276 return 0;
0277 }
0278
0279 *pI = p_cache->p_info[control_index];
0280 if (!*pI) {
0281 HPI_DEBUG_LOG(VERBOSE, "Uncached Control %d\n",
0282 control_index);
0283 return 0;
0284 } else {
0285 HPI_DEBUG_LOG(VERBOSE, "find_control() type %d\n",
0286 (*pI)->control_type);
0287 }
0288 return 1;
0289 }
0290
0291
0292 #define HPICMN_PAD_OFS_AND_SIZE(m) {\
0293 offsetof(struct hpi_control_cache_pad, m), \
0294 sizeof(((struct hpi_control_cache_pad *)(NULL))->m) }
0295
0296 struct pad_ofs_size {
0297 unsigned int offset;
0298 unsigned int field_size;
0299 };
0300
0301 static const struct pad_ofs_size pad_desc[] = {
0302 HPICMN_PAD_OFS_AND_SIZE(c_channel),
0303 HPICMN_PAD_OFS_AND_SIZE(c_artist),
0304 HPICMN_PAD_OFS_AND_SIZE(c_title),
0305 HPICMN_PAD_OFS_AND_SIZE(c_comment),
0306 };
0307
0308
0309
0310
0311 short hpi_check_control_cache_single(struct hpi_control_cache_single *pC,
0312 struct hpi_message *phm, struct hpi_response *phr)
0313 {
0314 size_t response_size;
0315 short found = 1;
0316
0317
0318 response_size =
0319 sizeof(struct hpi_response_header) +
0320 sizeof(struct hpi_control_res);
0321
0322 switch (pC->u.i.control_type) {
0323
0324 case HPI_CONTROL_METER:
0325 if (phm->u.c.attribute == HPI_METER_PEAK) {
0326 phr->u.c.an_log_value[0] = pC->u.meter.an_log_peak[0];
0327 phr->u.c.an_log_value[1] = pC->u.meter.an_log_peak[1];
0328 } else if (phm->u.c.attribute == HPI_METER_RMS) {
0329 if (pC->u.meter.an_logRMS[0] ==
0330 HPI_CACHE_INVALID_SHORT) {
0331 phr->error =
0332 HPI_ERROR_INVALID_CONTROL_ATTRIBUTE;
0333 phr->u.c.an_log_value[0] = HPI_METER_MINIMUM;
0334 phr->u.c.an_log_value[1] = HPI_METER_MINIMUM;
0335 } else {
0336 phr->u.c.an_log_value[0] =
0337 pC->u.meter.an_logRMS[0];
0338 phr->u.c.an_log_value[1] =
0339 pC->u.meter.an_logRMS[1];
0340 }
0341 } else
0342 found = 0;
0343 break;
0344 case HPI_CONTROL_VOLUME:
0345 if (phm->u.c.attribute == HPI_VOLUME_GAIN) {
0346 phr->u.c.an_log_value[0] = pC->u.vol.an_log[0];
0347 phr->u.c.an_log_value[1] = pC->u.vol.an_log[1];
0348 } else if (phm->u.c.attribute == HPI_VOLUME_MUTE) {
0349 if (pC->u.vol.flags & HPI_VOLUME_FLAG_HAS_MUTE) {
0350 if (pC->u.vol.flags & HPI_VOLUME_FLAG_MUTED)
0351 phr->u.c.param1 =
0352 HPI_BITMASK_ALL_CHANNELS;
0353 else
0354 phr->u.c.param1 = 0;
0355 } else {
0356 phr->error =
0357 HPI_ERROR_INVALID_CONTROL_ATTRIBUTE;
0358 phr->u.c.param1 = 0;
0359 }
0360 } else {
0361 found = 0;
0362 }
0363 break;
0364 case HPI_CONTROL_MULTIPLEXER:
0365 if (phm->u.c.attribute == HPI_MULTIPLEXER_SOURCE) {
0366 phr->u.c.param1 = pC->u.mux.source_node_type;
0367 phr->u.c.param2 = pC->u.mux.source_node_index;
0368 } else {
0369 found = 0;
0370 }
0371 break;
0372 case HPI_CONTROL_CHANNEL_MODE:
0373 if (phm->u.c.attribute == HPI_CHANNEL_MODE_MODE)
0374 phr->u.c.param1 = pC->u.mode.mode;
0375 else
0376 found = 0;
0377 break;
0378 case HPI_CONTROL_LEVEL:
0379 if (phm->u.c.attribute == HPI_LEVEL_GAIN) {
0380 phr->u.c.an_log_value[0] = pC->u.level.an_log[0];
0381 phr->u.c.an_log_value[1] = pC->u.level.an_log[1];
0382 } else
0383 found = 0;
0384 break;
0385 case HPI_CONTROL_TUNER:
0386 if (phm->u.c.attribute == HPI_TUNER_FREQ)
0387 phr->u.c.param1 = pC->u.tuner.freq_ink_hz;
0388 else if (phm->u.c.attribute == HPI_TUNER_BAND)
0389 phr->u.c.param1 = pC->u.tuner.band;
0390 else if (phm->u.c.attribute == HPI_TUNER_LEVEL_AVG)
0391 if (pC->u.tuner.s_level_avg ==
0392 HPI_CACHE_INVALID_SHORT) {
0393 phr->u.cu.tuner.s_level = 0;
0394 phr->error =
0395 HPI_ERROR_INVALID_CONTROL_ATTRIBUTE;
0396 } else
0397 phr->u.cu.tuner.s_level =
0398 pC->u.tuner.s_level_avg;
0399 else
0400 found = 0;
0401 break;
0402 case HPI_CONTROL_AESEBU_RECEIVER:
0403 if (phm->u.c.attribute == HPI_AESEBURX_ERRORSTATUS)
0404 phr->u.c.param1 = pC->u.aes3rx.error_status;
0405 else if (phm->u.c.attribute == HPI_AESEBURX_FORMAT)
0406 phr->u.c.param1 = pC->u.aes3rx.format;
0407 else
0408 found = 0;
0409 break;
0410 case HPI_CONTROL_AESEBU_TRANSMITTER:
0411 if (phm->u.c.attribute == HPI_AESEBUTX_FORMAT)
0412 phr->u.c.param1 = pC->u.aes3tx.format;
0413 else
0414 found = 0;
0415 break;
0416 case HPI_CONTROL_TONEDETECTOR:
0417 if (phm->u.c.attribute == HPI_TONEDETECTOR_STATE)
0418 phr->u.c.param1 = pC->u.tone.state;
0419 else
0420 found = 0;
0421 break;
0422 case HPI_CONTROL_SILENCEDETECTOR:
0423 if (phm->u.c.attribute == HPI_SILENCEDETECTOR_STATE) {
0424 phr->u.c.param1 = pC->u.silence.state;
0425 } else
0426 found = 0;
0427 break;
0428 case HPI_CONTROL_MICROPHONE:
0429 if (phm->u.c.attribute == HPI_MICROPHONE_PHANTOM_POWER)
0430 phr->u.c.param1 = pC->u.microphone.phantom_state;
0431 else
0432 found = 0;
0433 break;
0434 case HPI_CONTROL_SAMPLECLOCK:
0435 if (phm->u.c.attribute == HPI_SAMPLECLOCK_SOURCE)
0436 phr->u.c.param1 = pC->u.clk.source;
0437 else if (phm->u.c.attribute == HPI_SAMPLECLOCK_SOURCE_INDEX) {
0438 if (pC->u.clk.source_index ==
0439 HPI_CACHE_INVALID_UINT16) {
0440 phr->u.c.param1 = 0;
0441 phr->error =
0442 HPI_ERROR_INVALID_CONTROL_ATTRIBUTE;
0443 } else
0444 phr->u.c.param1 = pC->u.clk.source_index;
0445 } else if (phm->u.c.attribute == HPI_SAMPLECLOCK_SAMPLERATE)
0446 phr->u.c.param1 = pC->u.clk.sample_rate;
0447 else
0448 found = 0;
0449 break;
0450 case HPI_CONTROL_PAD:{
0451 struct hpi_control_cache_pad *p_pad;
0452 p_pad = (struct hpi_control_cache_pad *)pC;
0453
0454 if (!(p_pad->field_valid_flags & (1 <<
0455 HPI_CTL_ATTR_INDEX(phm->u.c.
0456 attribute)))) {
0457 phr->error =
0458 HPI_ERROR_INVALID_CONTROL_ATTRIBUTE;
0459 break;
0460 }
0461
0462 if (phm->u.c.attribute == HPI_PAD_PROGRAM_ID)
0463 phr->u.c.param1 = p_pad->pI;
0464 else if (phm->u.c.attribute == HPI_PAD_PROGRAM_TYPE)
0465 phr->u.c.param1 = p_pad->pTY;
0466 else {
0467 unsigned int index =
0468 HPI_CTL_ATTR_INDEX(phm->u.c.
0469 attribute) - 1;
0470 unsigned int offset = phm->u.c.param1;
0471 unsigned int pad_string_len, field_size;
0472 char *pad_string;
0473 unsigned int tocopy;
0474
0475 if (index > ARRAY_SIZE(pad_desc) - 1) {
0476 phr->error =
0477 HPI_ERROR_INVALID_CONTROL_ATTRIBUTE;
0478 break;
0479 }
0480
0481 pad_string =
0482 ((char *)p_pad) +
0483 pad_desc[index].offset;
0484 field_size = pad_desc[index].field_size;
0485
0486 pad_string[field_size - 1] = 0;
0487
0488 pad_string_len = strlen(pad_string) + 1;
0489
0490 if (offset > pad_string_len) {
0491 phr->error =
0492 HPI_ERROR_INVALID_CONTROL_VALUE;
0493 break;
0494 }
0495
0496 tocopy = pad_string_len - offset;
0497 if (tocopy > sizeof(phr->u.cu.chars8.sz_data))
0498 tocopy = sizeof(phr->u.cu.chars8.
0499 sz_data);
0500
0501 memcpy(phr->u.cu.chars8.sz_data,
0502 &pad_string[offset], tocopy);
0503
0504 phr->u.cu.chars8.remaining_chars =
0505 pad_string_len - offset - tocopy;
0506 }
0507 }
0508 break;
0509 default:
0510 found = 0;
0511 break;
0512 }
0513
0514 HPI_DEBUG_LOG(VERBOSE, "%s Adap %d, Ctl %d, Type %d, Attr %d\n",
0515 found ? "Cached" : "Uncached", phm->adapter_index,
0516 pC->u.i.control_index, pC->u.i.control_type,
0517 phm->u.c.attribute);
0518
0519 if (found) {
0520 phr->size = (u16)response_size;
0521 phr->type = HPI_TYPE_RESPONSE;
0522 phr->object = phm->object;
0523 phr->function = phm->function;
0524 }
0525
0526 return found;
0527 }
0528
0529 short hpi_check_control_cache(struct hpi_control_cache *p_cache,
0530 struct hpi_message *phm, struct hpi_response *phr)
0531 {
0532 struct hpi_control_cache_info *pI;
0533
0534 if (!find_control(phm->obj_index, p_cache, &pI)) {
0535 HPI_DEBUG_LOG(VERBOSE,
0536 "HPICMN find_control() failed for adap %d\n",
0537 phm->adapter_index);
0538 return 0;
0539 }
0540
0541 phr->error = 0;
0542 phr->specific_error = 0;
0543 phr->version = 0;
0544
0545 return hpi_check_control_cache_single((struct hpi_control_cache_single
0546 *)pI, phm, phr);
0547 }
0548
0549
0550
0551
0552
0553
0554
0555 void hpi_cmn_control_cache_sync_to_msg_single(struct hpi_control_cache_single
0556 *pC, struct hpi_message *phm, struct hpi_response *phr)
0557 {
0558 switch (pC->u.i.control_type) {
0559 case HPI_CONTROL_VOLUME:
0560 if (phm->u.c.attribute == HPI_VOLUME_GAIN) {
0561 pC->u.vol.an_log[0] = phr->u.c.an_log_value[0];
0562 pC->u.vol.an_log[1] = phr->u.c.an_log_value[1];
0563 } else if (phm->u.c.attribute == HPI_VOLUME_MUTE) {
0564 if (phm->u.c.param1)
0565 pC->u.vol.flags |= HPI_VOLUME_FLAG_MUTED;
0566 else
0567 pC->u.vol.flags &= ~HPI_VOLUME_FLAG_MUTED;
0568 }
0569 break;
0570 case HPI_CONTROL_MULTIPLEXER:
0571
0572 if (phm->u.c.attribute == HPI_MULTIPLEXER_SOURCE) {
0573 pC->u.mux.source_node_type = (u16)phm->u.c.param1;
0574 pC->u.mux.source_node_index = (u16)phm->u.c.param2;
0575 }
0576 break;
0577 case HPI_CONTROL_CHANNEL_MODE:
0578
0579 if (phm->u.c.attribute == HPI_CHANNEL_MODE_MODE)
0580 pC->u.mode.mode = (u16)phm->u.c.param1;
0581 break;
0582 case HPI_CONTROL_LEVEL:
0583 if (phm->u.c.attribute == HPI_LEVEL_GAIN) {
0584 pC->u.vol.an_log[0] = phr->u.c.an_log_value[0];
0585 pC->u.vol.an_log[1] = phr->u.c.an_log_value[1];
0586 }
0587 break;
0588 case HPI_CONTROL_MICROPHONE:
0589 if (phm->u.c.attribute == HPI_MICROPHONE_PHANTOM_POWER)
0590 pC->u.microphone.phantom_state = (u16)phm->u.c.param1;
0591 break;
0592 case HPI_CONTROL_AESEBU_TRANSMITTER:
0593 if (phm->u.c.attribute == HPI_AESEBUTX_FORMAT)
0594 pC->u.aes3tx.format = phm->u.c.param1;
0595 break;
0596 case HPI_CONTROL_AESEBU_RECEIVER:
0597 if (phm->u.c.attribute == HPI_AESEBURX_FORMAT)
0598 pC->u.aes3rx.format = phm->u.c.param1;
0599 break;
0600 case HPI_CONTROL_SAMPLECLOCK:
0601 if (phm->u.c.attribute == HPI_SAMPLECLOCK_SOURCE)
0602 pC->u.clk.source = (u16)phm->u.c.param1;
0603 else if (phm->u.c.attribute == HPI_SAMPLECLOCK_SOURCE_INDEX)
0604 pC->u.clk.source_index = (u16)phm->u.c.param1;
0605 else if (phm->u.c.attribute == HPI_SAMPLECLOCK_SAMPLERATE)
0606 pC->u.clk.sample_rate = phm->u.c.param1;
0607 break;
0608 default:
0609 break;
0610 }
0611 }
0612
0613 void hpi_cmn_control_cache_sync_to_msg(struct hpi_control_cache *p_cache,
0614 struct hpi_message *phm, struct hpi_response *phr)
0615 {
0616 struct hpi_control_cache_single *pC;
0617 struct hpi_control_cache_info *pI;
0618
0619 if (phr->error)
0620 return;
0621
0622 if (!find_control(phm->obj_index, p_cache, &pI)) {
0623 HPI_DEBUG_LOG(VERBOSE,
0624 "HPICMN find_control() failed for adap %d\n",
0625 phm->adapter_index);
0626 return;
0627 }
0628
0629
0630
0631
0632 pC = (struct hpi_control_cache_single *)pI;
0633
0634 hpi_cmn_control_cache_sync_to_msg_single(pC, phm, phr);
0635 }
0636
0637
0638
0639
0640
0641 struct hpi_control_cache *hpi_alloc_control_cache(const u32 control_count,
0642 const u32 size_in_bytes, u8 *p_dsp_control_buffer)
0643 {
0644 struct hpi_control_cache *p_cache =
0645 kmalloc(sizeof(*p_cache), GFP_KERNEL);
0646 if (!p_cache)
0647 return NULL;
0648
0649 p_cache->p_info =
0650 kcalloc(control_count, sizeof(*p_cache->p_info), GFP_KERNEL);
0651 if (!p_cache->p_info) {
0652 kfree(p_cache);
0653 return NULL;
0654 }
0655
0656 p_cache->cache_size_in_bytes = size_in_bytes;
0657 p_cache->control_count = control_count;
0658 p_cache->p_cache = p_dsp_control_buffer;
0659 p_cache->init = 0;
0660 return p_cache;
0661 }
0662
0663 void hpi_free_control_cache(struct hpi_control_cache *p_cache)
0664 {
0665 if (p_cache) {
0666 kfree(p_cache->p_info);
0667 kfree(p_cache);
0668 }
0669 }
0670
0671 static void subsys_message(struct hpi_message *phm, struct hpi_response *phr)
0672 {
0673 hpi_init_response(phr, HPI_OBJ_SUBSYSTEM, phm->function, 0);
0674
0675 switch (phm->function) {
0676 case HPI_SUBSYS_OPEN:
0677 case HPI_SUBSYS_CLOSE:
0678 case HPI_SUBSYS_DRIVER_UNLOAD:
0679 break;
0680 case HPI_SUBSYS_DRIVER_LOAD:
0681 wipe_adapter_list();
0682 hpios_alistlock_init(&adapters);
0683 break;
0684 case HPI_SUBSYS_GET_ADAPTER:
0685 subsys_get_adapter(phm, phr);
0686 break;
0687 case HPI_SUBSYS_GET_NUM_ADAPTERS:
0688 phr->u.s.num_adapters = adapters.gw_num_adapters;
0689 break;
0690 case HPI_SUBSYS_CREATE_ADAPTER:
0691 break;
0692 default:
0693 phr->error = HPI_ERROR_INVALID_FUNC;
0694 break;
0695 }
0696 }
0697
0698 void HPI_COMMON(struct hpi_message *phm, struct hpi_response *phr)
0699 {
0700 switch (phm->type) {
0701 case HPI_TYPE_REQUEST:
0702 switch (phm->object) {
0703 case HPI_OBJ_SUBSYSTEM:
0704 subsys_message(phm, phr);
0705 break;
0706 }
0707 break;
0708
0709 default:
0710 phr->error = HPI_ERROR_INVALID_TYPE;
0711 break;
0712 }
0713 }