/* API: init driver */ PJ_DEF(pj_status_t) pjmedia_vid_driver_init(unsigned drv_idx, pj_bool_t refresh) { pjmedia_vid_driver *drv = &vid_subsys.drv[drv_idx]; pjmedia_vid_dev_factory *f; unsigned i, dev_cnt; pj_status_t status; if (!refresh) { /* Create the factory */ f = (*drv->create)(vid_subsys.pf); if (!f) return PJ_EUNKNOWN; /* Call factory->init() */ status = f->op->init(f); if (status != PJ_SUCCESS) { f->op->destroy(f); return status; } } else { f = drv->f; } /* Get number of devices */ dev_cnt = f->op->get_dev_count(f); if (dev_cnt + vid_subsys.dev_cnt > MAX_DEVS) { PJ_LOG(4,(THIS_FILE, "%d device(s) cannot be registered because" " there are too many devices", vid_subsys.dev_cnt + dev_cnt - MAX_DEVS)); dev_cnt = MAX_DEVS - vid_subsys.dev_cnt; } /* enabling this will cause pjsua-lib initialization to fail when there * is no video device installed in the system, even when pjsua has been * run with --null-video * if (dev_cnt == 0) { f->op->destroy(f); return PJMEDIA_EVID_NODEV; } */ /* Fill in default devices */ drv->rend_dev_idx = drv->cap_dev_idx = -1; for (i=0; i<dev_cnt; ++i) { pjmedia_vid_dev_info info; status = f->op->get_dev_info(f, i, &info); if (status != PJ_SUCCESS) { f->op->destroy(f); return status; } if (drv->name[0]=='\0') { /* Set driver name */ pj_ansi_strncpy(drv->name, info.driver, sizeof(drv->name)); drv->name[sizeof(drv->name)-1] = '\0'; } if (drv->rend_dev_idx < 0 && (info.dir & PJMEDIA_DIR_RENDER)) { /* Set default render device */ drv->rend_dev_idx = i; } if (drv->cap_dev_idx < 0 && (info.dir & PJMEDIA_DIR_CAPTURE)) { /* Set default capture device */ drv->cap_dev_idx = i; } if (drv->rend_dev_idx >= 0 && drv->cap_dev_idx >= 0) { /* Done. */ break; } } /* Register the factory */ drv->f = f; drv->f->sys.drv_idx = drv_idx; drv->start_idx = vid_subsys.dev_cnt; drv->dev_cnt = dev_cnt; /* Register devices to global list */ for (i=0; i<dev_cnt; ++i) { vid_subsys.dev_list[vid_subsys.dev_cnt++] = MAKE_DEV_ID(drv_idx, i); } return PJ_SUCCESS; }
/* Internal: init driver */ static pj_status_t init_driver(unsigned drv_idx, pj_bool_t refresh) { struct driver *drv = &aud_subsys.drv[drv_idx]; pjmedia_aud_dev_factory *f; unsigned i, dev_cnt; pj_status_t status; if (!refresh && drv->create) { /* Create the factory */ f = (*drv->create)(aud_subsys.pf); if (!f) return PJ_EUNKNOWN; /* Call factory->init() */ status = f->op->init(f); if (status != PJ_SUCCESS) { f->op->destroy(f); return status; } } else { f = drv->f; } /* Register device change observer */ if (!refresh) { f->op->set_dev_change_cb(f, &process_aud_dev_change_event); } if (!f) return PJ_EUNKNOWN; /* Get number of devices */ dev_cnt = f->op->get_dev_count(f); if (dev_cnt + aud_subsys.dev_cnt > MAX_DEVS) { PJ_LOG(4,(THIS_FILE, "%d device(s) cannot be registered because" " there are too many devices", aud_subsys.dev_cnt + dev_cnt - MAX_DEVS)); dev_cnt = MAX_DEVS - aud_subsys.dev_cnt; } /* enabling this will cause pjsua-lib initialization to fail when there * is no sound device installed in the system, even when pjsua has been * run with --null-audio * if (dev_cnt == 0) { f->op->destroy(f); return PJMEDIA_EAUD_NODEV; } */ /* Fill in default devices */ drv->rec_dev_idx = f->op->get_default_rec_dev(f); drv->play_dev_idx = f->op->get_default_play_dev(f); for (i=0; i<dev_cnt; ++i) { pjmedia_aud_dev_info info; status = f->op->get_dev_info(f, i, &info); if (status != PJ_SUCCESS) { f->op->destroy(f); return status; } if (drv->name[0]=='\0') { /* Set driver name */ pj_ansi_strncpy(drv->name, info.driver, sizeof(drv->name)); drv->name[sizeof(drv->name)-1] = '\0'; } if (drv->play_dev_idx < 0 && info.output_count) { /* Set default playback device */ drv->play_dev_idx = i; } if (drv->rec_dev_idx < 0 && info.input_count) { /* Set default capture device */ drv->rec_dev_idx = i; } if (drv->play_dev_idx >= 0 && drv->rec_dev_idx >= 0) { /* Done. */ break; } } /* Register the factory */ drv->f = f; drv->f->sys.drv_idx = drv_idx; drv->start_idx = aud_subsys.dev_cnt; drv->dev_cnt = dev_cnt; /* Register devices to global list */ for (i=0; i<dev_cnt; ++i) { aud_subsys.dev_list[aud_subsys.dev_cnt++] = MAKE_DEV_ID(drv_idx, i); } return PJ_SUCCESS; }