factory.c 12.1 KB
Newer Older
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19
/*
linphone
Copyright (C) 2016 Belledonne Communications <info@belledonne-communications.com>

This program is free software; you can redistribute it and/or
modify it under the terms of the GNU General Public License
as published by the Free Software Foundation; either version 2
of the License, or (at your option) any later version.

This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
GNU General Public License for more details.

You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
*/

20
#include "linphone/factory.h"
21 22

#include "c-wrapper/c-wrapper.h"
23

24
#ifndef PACKAGE_SOUND_DIR
25
	#define PACKAGE_SOUND_DIR "."
26 27
#endif
#ifndef PACKAGE_RING_DIR
28
	#define PACKAGE_RING_DIR "."
29 30 31
#endif

#ifndef PACKAGE_DATA_DIR
32
	#define PACKAGE_DATA_DIR "."
33 34
#endif

35 36 37 38 39 40 41
extern LinphoneCore *_linphone_core_new_with_config(LinphoneCoreCbs *cbs, struct _LpConfig *config, void *userdata);
extern LinphoneAddress *_linphone_address_new(const char *addr);

typedef belle_sip_object_t_vptr_t LinphoneFactory_vptr_t;

struct _LinphoneFactory {
	belle_sip_object_t base;
42 43 44

	bctbx_list_t *supported_video_definitions;

Simon Morlat's avatar
Simon Morlat committed
45
	/*these are the directories set by the application*/
46 47 48 49 50 51
	char *top_resources_dir;
	char *data_resources_dir;
	char *sound_resources_dir;
	char *ring_resources_dir;
	char *image_resources_dir;
	char *msplugins_dir;
52

Simon Morlat's avatar
Simon Morlat committed
53 54 55 56 57 58
	/*these are the cached result computed from directories set by the application*/
	char *cached_data_resources_dir;
	char *cached_sound_resources_dir;
	char *cached_ring_resources_dir;
	char *cached_image_resources_dir;
	char *cached_msplugins_dir;
59
	LinphoneErrorInfo* ei;
60 61
};

Simon Morlat's avatar
Simon Morlat committed
62
static void linphone_factory_uninit(LinphoneFactory *obj){
63 64
	bctbx_list_free_with_data(obj->supported_video_definitions, (bctbx_list_free_func)linphone_video_definition_unref);

Simon Morlat's avatar
Simon Morlat committed
65 66 67 68 69 70
	STRING_RESET(obj->top_resources_dir);
	STRING_RESET(obj->data_resources_dir);
	STRING_RESET(obj->sound_resources_dir);
	STRING_RESET(obj->ring_resources_dir);
	STRING_RESET(obj->image_resources_dir);
	STRING_RESET(obj->msplugins_dir);
71

Simon Morlat's avatar
Simon Morlat committed
72 73 74 75 76 77 78
	STRING_RESET(obj->cached_data_resources_dir);
	STRING_RESET(obj->cached_sound_resources_dir);
	STRING_RESET(obj->cached_ring_resources_dir);
	STRING_RESET(obj->cached_image_resources_dir);
	STRING_RESET(obj->cached_msplugins_dir);
}

79 80
BELLE_SIP_DECLARE_NO_IMPLEMENTED_INTERFACES(LinphoneFactory);
BELLE_SIP_INSTANCIATE_VPTR(LinphoneFactory, belle_sip_object_t,
Simon Morlat's avatar
Simon Morlat committed
81
	linphone_factory_uninit, // destroy
82 83 84 85 86 87 88 89 90 91 92 93 94 95
	NULL, // clone
	NULL, // Marshall
	FALSE
);

static LinphoneFactory *_factory = NULL;

static void _linphone_factory_destroying_cb(void) {
	if (_factory != NULL) {
		belle_sip_object_unref(_factory);
		_factory = NULL;
	}
}

96 97
#define ADD_SUPPORTED_VIDEO_DEFINITION(factory, width, height, name) \
	(factory)->supported_video_definitions = bctbx_list_append((factory)->supported_video_definitions, \
98
		linphone_video_definition_new(width, height, name))
99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126

static void initialize_supported_video_definitions(LinphoneFactory *factory) {
#if !defined(__ANDROID__) && !TARGET_OS_IPHONE
	ADD_SUPPORTED_VIDEO_DEFINITION(factory, MS_VIDEO_SIZE_1080P_W, MS_VIDEO_SIZE_1080P_H, "1080p");
#endif
#if !defined(__ANDROID__) && !TARGET_OS_MAC /*limit to most common sizes because mac video API cannot list supported resolutions*/
	ADD_SUPPORTED_VIDEO_DEFINITION(factory, MS_VIDEO_SIZE_UXGA_W, MS_VIDEO_SIZE_UXGA_H, "uxga");
	ADD_SUPPORTED_VIDEO_DEFINITION(factory, MS_VIDEO_SIZE_SXGA_MINUS_W, MS_VIDEO_SIZE_SXGA_MINUS_H, "sxga-");
#endif
	ADD_SUPPORTED_VIDEO_DEFINITION(factory, MS_VIDEO_SIZE_720P_W, MS_VIDEO_SIZE_720P_H, "720p");
#if !defined(__ANDROID__) && !TARGET_OS_MAC
	ADD_SUPPORTED_VIDEO_DEFINITION(factory, MS_VIDEO_SIZE_XGA_W, MS_VIDEO_SIZE_XGA_H, "xga");
#endif
#if !defined(__ANDROID__) && !TARGET_OS_IPHONE
	ADD_SUPPORTED_VIDEO_DEFINITION(factory, MS_VIDEO_SIZE_SVGA_W, MS_VIDEO_SIZE_SVGA_H, "svga");
	ADD_SUPPORTED_VIDEO_DEFINITION(factory, MS_VIDEO_SIZE_4CIF_W, MS_VIDEO_SIZE_4CIF_H, "4cif");
#endif
	ADD_SUPPORTED_VIDEO_DEFINITION(factory, MS_VIDEO_SIZE_VGA_W, MS_VIDEO_SIZE_VGA_H, "vga");
#if TARGET_OS_IPHONE
	ADD_SUPPORTED_VIDEO_DEFINITION(factory, MS_VIDEO_SIZE_IOS_MEDIUM_H, MS_VIDEO_SIZE_IOS_MEDIUM_W, "ios-medium");
#endif
	ADD_SUPPORTED_VIDEO_DEFINITION(factory, MS_VIDEO_SIZE_CIF_W, MS_VIDEO_SIZE_CIF_H, "cif");
#if !TARGET_OS_MAC || TARGET_OS_IPHONE /* OS_MAC is 1 for iPhone, but we need QVGA */
	ADD_SUPPORTED_VIDEO_DEFINITION(factory, MS_VIDEO_SIZE_QVGA_W, MS_VIDEO_SIZE_QVGA_H, "qvga");
#endif
	ADD_SUPPORTED_VIDEO_DEFINITION(factory, MS_VIDEO_SIZE_QCIF_W, MS_VIDEO_SIZE_QCIF_H, "qcif");
}

Simon Morlat's avatar
Simon Morlat committed
127 128 129
static LinphoneFactory *linphone_factory_new(void){
	LinphoneFactory *factory = belle_sip_object_new(LinphoneFactory);
	factory->top_resources_dir = bctbx_strdup(PACKAGE_DATA_DIR);
130
	initialize_supported_video_definitions(factory);
Simon Morlat's avatar
Simon Morlat committed
131 132 133 134
	return factory;
}


135 136
LinphoneFactory *linphone_factory_get(void) {
	if (_factory == NULL) {
Simon Morlat's avatar
Simon Morlat committed
137
		_factory = linphone_factory_new();
138 139 140 141 142
		atexit(_linphone_factory_destroying_cb);
	}
	return _factory;
}

Simon Morlat's avatar
Simon Morlat committed
143 144 145 146 147 148 149
void linphone_factory_clean(void){
	if (_factory){
		belle_sip_object_unref(_factory);
		_factory = NULL;
	}
}

150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166
LinphoneCore *linphone_factory_create_core(const LinphoneFactory *factory, LinphoneCoreCbs *cbs,
		const char *config_path, const char *factory_config_path) {
	LpConfig *config = lp_config_new_with_factory(config_path, factory_config_path);
	LinphoneCore *lc = _linphone_core_new_with_config(cbs, config, NULL);
	lp_config_unref(config);
	return lc;
}

LinphoneCore *linphone_factory_create_core_with_config(const LinphoneFactory *factory, LinphoneCoreCbs *cbs, LinphoneConfig *config) {
	return _linphone_core_new_with_config(cbs, config, NULL);
}

LinphoneCoreCbs *linphone_factory_create_core_cbs(const LinphoneFactory *factory) {
	return _linphone_core_cbs_new();
}

LinphoneAddress *linphone_factory_create_address(const LinphoneFactory *factory, const char *addr) {
167
	return linphone_address_new(addr);
168 169 170 171 172
}

LinphoneAuthInfo *linphone_factory_create_auth_info(const LinphoneFactory *factory, const char *username, const char *userid, const char *passwd, const char *ha1, const char *realm, const char *domain) {
	return linphone_auth_info_new(username, userid, passwd, ha1, realm, domain);
}
173

174 175 176 177
LinphoneCallCbs * linphone_factory_create_call_cbs(const LinphoneFactory *factory) {
	return _linphone_call_cbs_new();
}

178
LinphoneVcard *linphone_factory_create_vcard(LinphoneFactory *factory) {
Simon Morlat's avatar
Simon Morlat committed
179
	return _linphone_vcard_new();
180
}
181

182
LinphoneVideoDefinition * linphone_factory_create_video_definition(const LinphoneFactory *factory, unsigned int width, unsigned int height) {
183 184
	LinphoneVideoDefinition *supported = linphone_factory_find_supported_video_definition(factory, width, height);
	return supported ? linphone_video_definition_clone(supported) : linphone_video_definition_new(width, height, NULL);
185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205
}

LinphoneVideoDefinition * linphone_factory_create_video_definition_from_name(const LinphoneFactory *factory, const char *name) {
	unsigned int width = 0;
	unsigned int height = 0;
	LinphoneVideoDefinition *vdef = linphone_factory_find_supported_video_definition_by_name(factory, name);
	if (vdef != NULL) return vdef;
	if (sscanf(name, "%ux%u", &width, &height) == 2) {
		return linphone_video_definition_new(width, height, NULL);
	}
	return linphone_video_definition_new(0, 0, NULL);
}

const bctbx_list_t * linphone_factory_get_supported_video_definitions(const LinphoneFactory *factory) {
	return factory->supported_video_definitions;
}

LinphoneVideoDefinition * linphone_factory_find_supported_video_definition(const LinphoneFactory *factory, unsigned int width, unsigned int height) {
	const bctbx_list_t *item;
	const bctbx_list_t *supported = linphone_factory_get_supported_video_definitions(factory);
	LinphoneVideoDefinition *searched_vdef = linphone_video_definition_new(width, height, NULL);
206
	LinphoneVideoDefinition *found = NULL;
207 208 209 210

	for (item = supported; item != NULL; item = bctbx_list_next(item)) {
		LinphoneVideoDefinition *svdef = (LinphoneVideoDefinition *)bctbx_list_get_data(item);
		if (linphone_video_definition_equals(svdef, searched_vdef)) {
211 212
			found = svdef;
			break;
213 214
		}
	}
215 216
	linphone_video_definition_unref(searched_vdef);
	return found;
217 218 219 220 221 222 223 224 225
}

LinphoneVideoDefinition * linphone_factory_find_supported_video_definition_by_name(const LinphoneFactory *factory, const char *name) {
	const bctbx_list_t *item;
	const bctbx_list_t *supported = linphone_factory_get_supported_video_definitions(factory);

	for (item = supported; item != NULL; item = bctbx_list_next(item)) {
		LinphoneVideoDefinition *svdef = (LinphoneVideoDefinition *)bctbx_list_get_data(item);
		if (strcmp(linphone_video_definition_get_name(svdef), name) == 0) {
226
			return svdef;
227 228 229 230 231
		}
	}
	return NULL;
}

Simon Morlat's avatar
Simon Morlat committed
232 233
const char * linphone_factory_get_top_resources_dir(const LinphoneFactory *factory) {
	return factory->top_resources_dir;
234 235 236
}

void linphone_factory_set_top_resources_dir(LinphoneFactory *factory, const char *path) {
Simon Morlat's avatar
Simon Morlat committed
237
	STRING_SET(factory->top_resources_dir, path);
238 239
}

Simon Morlat's avatar
Simon Morlat committed
240 241 242 243 244 245 246 247
const char * linphone_factory_get_data_resources_dir(LinphoneFactory *factory) {
	if (factory->data_resources_dir) return factory->data_resources_dir;
	if (factory->top_resources_dir){
		STRING_TRANSFER(factory->cached_data_resources_dir, bctbx_strdup_printf("%s/linphone", factory->top_resources_dir));
	}else{
		STRING_TRANSFER(factory->cached_data_resources_dir, bctbx_strdup_printf("%s/linphone", PACKAGE_DATA_DIR));
	}
	return factory->cached_data_resources_dir;
248 249 250
}

void linphone_factory_set_data_resources_dir(LinphoneFactory *factory, const char *path) {
Simon Morlat's avatar
Simon Morlat committed
251
	STRING_SET(factory->data_resources_dir, path);
252 253
}

Simon Morlat's avatar
Simon Morlat committed
254 255 256 257 258 259 260
const char * linphone_factory_get_sound_resources_dir(LinphoneFactory *factory) {
	if (factory->sound_resources_dir) return factory->sound_resources_dir;
	if (factory->top_resources_dir){
		STRING_TRANSFER(factory->cached_sound_resources_dir, bctbx_strdup_printf("%s/sounds/linphone", factory->top_resources_dir));
		return factory->cached_sound_resources_dir;
	}
	return PACKAGE_SOUND_DIR;
261 262 263
}

void linphone_factory_set_sound_resources_dir(LinphoneFactory *factory, const char *path) {
Simon Morlat's avatar
Simon Morlat committed
264
	STRING_SET(factory->sound_resources_dir, path);
265 266
}

Simon Morlat's avatar
Simon Morlat committed
267 268 269
const char * linphone_factory_get_ring_resources_dir(LinphoneFactory *factory) {
	if (factory->ring_resources_dir) return factory->ring_resources_dir;
	if (factory->sound_resources_dir){
270 271 272 273 274 275
		STRING_TRANSFER(factory->cached_ring_resources_dir, bctbx_strdup_printf("%s/rings", factory->sound_resources_dir));
		return factory->cached_ring_resources_dir;
	}
	if (factory->top_resources_dir) {
		STRING_TRANSFER(factory->cached_ring_resources_dir, bctbx_strdup_printf("%s/sounds/linphone/rings", factory->top_resources_dir));
		return factory->cached_ring_resources_dir;
Simon Morlat's avatar
Simon Morlat committed
276 277
	}
	return PACKAGE_RING_DIR;
278 279 280
}

void linphone_factory_set_ring_resources_dir(LinphoneFactory *factory, const char *path) {
Simon Morlat's avatar
Simon Morlat committed
281
	STRING_SET(factory->ring_resources_dir, path);
282 283
}

Simon Morlat's avatar
Simon Morlat committed
284 285 286 287 288 289 290 291
const char * linphone_factory_get_image_resources_dir(LinphoneFactory *factory) {
	if (factory->image_resources_dir) return factory->image_resources_dir;
	if (factory->top_resources_dir) {
		STRING_TRANSFER(factory->cached_image_resources_dir, bctbx_strdup_printf("%s/images", factory->top_resources_dir));
	}else{
		STRING_TRANSFER(factory->cached_image_resources_dir, bctbx_strdup_printf("%s/images", PACKAGE_DATA_DIR));
	}
	return factory->cached_image_resources_dir;
292 293 294
}

void linphone_factory_set_image_resources_dir(LinphoneFactory *factory, const char *path) {
Simon Morlat's avatar
Simon Morlat committed
295
	STRING_SET(factory->image_resources_dir, path);
296 297
}

Simon Morlat's avatar
Simon Morlat committed
298 299
const char * linphone_factory_get_msplugins_dir(LinphoneFactory *factory) {
	return factory->msplugins_dir;
300 301 302
}

void linphone_factory_set_msplugins_dir(LinphoneFactory *factory, const char *path) {
Simon Morlat's avatar
Simon Morlat committed
303
	STRING_SET(factory->msplugins_dir, path);
304
}
305

306
LinphoneErrorInfo *linphone_factory_create_error_info(LinphoneFactory *factory){
307

308
	return linphone_error_info_new();
309

310
}
311 312 313

LinphoneRange *linphone_factory_create_range(LinphoneFactory *factory) {
	return linphone_range_new();
314 315 316 317 318 319 320 321
}

LinphoneTransports *linphone_factory_create_transports(LinphoneFactory *factory) {
	return linphone_transports_new();
}

LinphoneVideoActivationPolicy *linphone_factory_create_video_activation_policy(LinphoneFactory *factory) {
	return linphone_video_activation_policy_new();
322
}