c语言context,context.c

/*

* libiio - Library for interfacing industrial I/O (IIO) devices

*

* Copyright (C) 2014 Analog Devices, Inc.

* Author: Paul Cercueil

*

* This library is free software; you can redistribute it and/or

* modify it under the terms of the GNU Lesser General Public

* License as published by the Free Software Foundation; either

* version 2.1 of the License, or (at your option) any later version.

*

* This library 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

* Lesser General Public License for more details.

*

* */

#include "debug.h"

#include "iio-config.h"

#include "iio-private.h"

#include "sort.h"

#include

#include

#ifdef _WIN32

#define LOCAL_BACKEND 0

#define NETWORK_BACKEND 1

#endif

static const char xml_header[] = "<?xml version=\"1.0\" encoding=\"utf-8\"?>"

""

""

""

""

""

""

""

""

""

""

""

""

""

""

""

""

""

"]>";

/* Returns a string containing the XML representation of this context */

char * iio_context_create_xml(const struct iio_context *ctx)

{

size_t len, *devices_len = NULL;

char *str, *ptr, **devices = NULL;

unsigned int i;

len = strlen(ctx->name) + sizeof(xml_header) - 1 +

sizeof("");

if (ctx->description)

len += strlen(ctx->description) +

sizeof(" description=\"\"") - 1;

for (i = 0; i < ctx->nb_attrs; i++)

len += strlen(ctx->attrs[i]) +

strlen(ctx->values[i]) +

sizeof("");

if (ctx->nb_devices) {

devices_len = malloc(ctx->nb_devices * sizeof(*devices_len));

if (!devices_len) {

errno = ENOMEM;

return NULL;

}

devices = calloc(ctx->nb_devices, sizeof(*devices));

if (!devices)

goto err_free_devices_len;

for (i = 0; i < ctx->nb_devices; i++) {

char *xml = iio_device_get_xml(ctx->devices[i],

&devices_len[i]);

if (!xml)

goto err_free_devices;

devices[i] = xml;

len += devices_len[i];

}

}

str = malloc(len);

if (!str) {

errno = ENOMEM;

goto err_free_devices;

}

if (ctx->description) {

iio_snprintf(str, len, "%s

"description=\"%s\" >",

xml_header, ctx->name, ctx->description);

} else {

iio_snprintf(str, len, "%s",

xml_header, ctx->name);

}

ptr = strrchr(str, '\0');

for (i = 0; i < ctx->nb_attrs; i++)

ptr += sprintf(ptr, "",

ctx->attrs[i], ctx->values[i]);

for (i = 0; i < ctx->nb_devices; i++) {

strcpy(ptr, devices[i]);

ptr += devices_len[i];

free(devices[i]);

}

free(devices);

free(devices_len);

strcpy(ptr, "

");

return str;

err_free_devices:

for (i = 0; i < ctx->nb_devices; i++)

free(devices[i]);

free(devices);

err_free_devices_len:

free(devices_len);

return NULL;

}

const char * iio_context_get_xml(const struct iio_context *ctx)

{

return ctx->xml;

}

const char * iio_context_get_name(const struct iio_context *ctx)

{

return ctx->name;

}

const char * iio_context_get_description(const struct iio_context *ctx)

{

if (ctx->description)

return ctx->description;

else

return "";

}

void iio_context_destroy(struct iio_context *ctx)

{

unsigned int i;

if (ctx->ops->shutdown)

ctx->ops->shutdown(ctx);

for (i = 0; i < ctx->nb_attrs; i++) {

free(ctx->attrs[i]);

free(ctx->values[i]);

}

if (ctx->nb_attrs) {

free(ctx->attrs);

free(ctx->values);

}

for (i = 0; i < ctx->nb_devices; i++)

free_device(ctx->devices[i]);

if (ctx->nb_devices)

free(ctx->devices);

if (ctx->xml)

free(ctx->xml);

if (ctx->description)

free(ctx->description);

free(ctx);

}

unsigned int iio_context_get_devices_count(const struct iio_context *ctx)

{

return ctx->nb_devices;

}

struct iio_device * iio_context_get_device(const struct iio_context *ctx,

unsigned int index)

{

if (index >= ctx->nb_devices)

return NULL;

else

return ctx->devices[index];

}

struct iio_device * iio_context_find_device(const struct iio_context *ctx,

const char *name)

{

unsigned int i;

for (i = 0; i < ctx->nb_devices; i++) {

struct iio_device *dev = ctx->devices[i];

if (!strcmp(dev->id, name) ||

(dev->name && !strcmp(dev->name, name)))

return dev;

}

return NULL;

}

static void reorder_channels(struct iio_device *dev)

{

bool found;

unsigned int i;

/* Reorder channels by index */

do {

found = false;

for (i = 1; i < dev->nb_channels; i++) {

struct iio_channel **channels = dev->channels;

long ch1 = channels[i - 1]->index;

long ch2 = channels[i]->index;

if (ch1 == ch2 && ch1 >= 0) {

ch1 = channels[i - 1]->format.shift;

ch2 = channels[i]->format.shift;

}

if (ch2 >= 0 && ((ch1 > ch2) || ch1 < 0)) {

struct iio_channel *bak = channels[i];

channels[i] = channels[i - 1];

channels[i - 1] = bak;

found = true;

}

}

} while (found);

for (i = 0; i < dev->nb_channels; i++)

dev->channels[i]->number = i;

}

int iio_context_init(struct iio_context *ctx)

{

unsigned int i;

for (i = 0; i < ctx->nb_devices; i++)

reorder_channels(ctx->devices[i]);

if (!ctx->xml) {

ctx->xml = iio_context_create_xml(ctx);

if (!ctx->xml)

return -ENOMEM;

}

return 0;

}

int iio_context_get_version(const struct iio_context *ctx,

unsigned int *major, unsigned int *minor, char git_tag[8])

{

if (ctx->ops->get_version)

return ctx->ops->get_version(ctx, major, minor, git_tag);

iio_library_get_version(major, minor, git_tag);

return 0;

}

int iio_context_set_timeout(struct iio_context *ctx, unsigned int timeout)

{

if (ctx->ops->set_timeout)

return ctx->ops->set_timeout(ctx, timeout);

else

return -ENOSYS;

}

struct iio_context * iio_context_clone(const struct iio_context *ctx)

{

if (ctx->ops->clone) {

return ctx->ops->clone(ctx);

} else {

errno = ENOSYS;

return NULL;

}

}

struct iio_context * iio_create_context_from_uri(const char *uri)

{

#ifdef WITH_LOCAL_BACKEND

if (strcmp(uri, "local:") == 0) /* No address part */

return iio_create_local_context();

#endif

#ifdef WITH_XML_BACKEND

if (strncmp(uri, "xml:", sizeof("xml:") - 1) == 0)

return iio_create_xml_context(uri + sizeof("xml:") - 1);

#endif

#ifdef WITH_NETWORK_BACKEND

if (strncmp(uri, "ip:", sizeof("ip:") - 1) == 0)

return iio_create_network_context(uri+3);

#endif

#ifdef WITH_USB_BACKEND

if (strncmp(uri, "usb:", sizeof("usb:") - 1) == 0)

return usb_create_context_from_uri(uri);

#endif

#ifdef WITH_SERIAL_BACKEND

if (strncmp(uri, "serial:", sizeof("serial:") - 1) == 0)

return serial_create_context_from_uri(uri);

#endif

errno = ENOSYS;

return NULL;

}

struct iio_context * iio_create_default_context(void)

{

char *hostname = getenv("IIOD_REMOTE");

if (hostname) {

struct iio_context *ctx;

ctx = iio_create_context_from_uri(hostname);

if (ctx)

return ctx;

#ifdef WITH_NETWORK_BACKEND

/* If the environment variable is an empty string, we will

* discover the server using ZeroConf */

if (strlen(hostname) == 0)

hostname = NULL;

return iio_create_network_context(hostname);

#endif

}

return iio_create_local_context();

}

struct iio_context * iio_create_local_context(void)

{

#ifdef WITH_LOCAL_BACKEND

return local_create_context();

#else

errno = ENOSYS;

return NULL;

#endif

}

struct iio_context * iio_create_network_context(const char *hostname)

{

#ifdef WITH_NETWORK_BACKEND

return network_create_context(hostname);

#else

errno = ENOSYS;

return NULL;

#endif

}

struct iio_context * iio_create_xml_context_mem(const char *xml, size_t len)

{

#ifdef WITH_XML_BACKEND

return xml_create_context_mem(xml, len);

#else

errno = ENOSYS;

return NULL;

#endif

}

struct iio_context * iio_create_xml_context(const char *xml_file)

{

#ifdef WITH_XML_BACKEND

return xml_create_context(xml_file);

#else

errno = ENOSYS;

return NULL;

#endif

}

unsigned int iio_context_get_attrs_count(const struct iio_context *ctx)

{

return ctx->nb_attrs;

}

int iio_context_get_attr(const struct iio_context *ctx, unsigned int index,

const char **name, const char **value)

{

if (index >= ctx->nb_attrs)

return -EINVAL;

if (name)

*name = ctx->attrs[index];

if (value)

*value = ctx->values[index];

return 0;

}

const char * iio_context_get_attr_value(

const struct iio_context *ctx, const char *name)

{

unsigned int i;

for (i = 0; i < ctx->nb_attrs; i++) {

if (!strcmp(name, ctx->attrs[i]))

return ctx->values[i];

}

return NULL;

}

int iio_context_add_attr(struct iio_context *ctx,

const char *key, const char *value)

{

char **attrs, **values, *new_key, *new_val;

attrs = realloc(ctx->attrs,

(ctx->nb_attrs + 1) * sizeof(*ctx->attrs));

if (!attrs)

return -ENOMEM;

ctx->attrs = attrs;

values = realloc(ctx->values,

(ctx->nb_attrs + 1) * sizeof(*ctx->values));

if (!values)

return -ENOMEM;

ctx->values = values;

new_key = iio_strdup(key);

if (!new_key)

return -ENOMEM;

new_val = iio_strdup(value);

if (!new_val) {

free(new_key);

return -ENOMEM;

}

ctx->attrs[ctx->nb_attrs] = new_key;

ctx->values[ctx->nb_attrs] = new_val;

ctx->nb_attrs++;

return 0;

}

一键复制

编辑

Web IDE

原始数据

按行查看

历史

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值