Add video recorder and playback support.
| | |
| | | RM := rm
|
| | |
|
| | | CFLAGS += -c -Wall -DWITH_DOM -DWITH_NONAMESPACES -DWITH_OPENSSL
|
| | | CFLAGS += -DPROTOBUF_USS_DLLS
|
| | | CFLAGS += -fPIC -Wunused-function
|
| | |
|
| | | SOURCES_CORE += \
|
| | | core/soapC.c \
|
| | |
| | | service/probe/probe.c \
|
| | | service/deviceinfo/dev_info.c \
|
| | | service/capabilities/capa.c \
|
| | | service/ptz/ptz.c |
| | | service/ptz/ptz.c \
|
| | | service/av_demux/av_demux.c |
| | |
|
| | | SOURCES_COMM += \
|
| | | comm/proto_dbg.c \
|
| | |
| | | OBJECTS_ONVIF_SRVS := $(patsubst %.c,$(TEMPDIR)%.o,$(filter %.c, $(SOURCES_SRVS)))
|
| | | OBJECTS_ONVIF_COMM := $(patsubst %.c,$(TEMPDIR)%.o,$(filter %.c, $(SOURCES_COMM)))
|
| | |
|
| | | FFMPEG_DIR = thirdparty/ffmpeg
|
| | | OPENSSL_DIR = thirdparty/openssl
|
| | |
|
| | | TARGET_LIB = libonvif_std.so
|
| | |
| | | INCLUDE += -Icore/ \
|
| | | -Icomm/ \
|
| | | -Iservice \
|
| | | -I$(FFMPEG_DIR)/include \
|
| | | -I$(OPENSSL_DIR)/include
|
| | | CFLAGS += $(INCLUDE)
|
| | |
|
| | | CFLAGS += -Wno-unused
|
| | | LDFLAGS += -L$(FFMPEG_DIR)/lib
|
| | | LDFLAGS += -L$(OPENSSL_DIR)/lib
|
| | | LDFLAGS += -Lthirdparty
|
| | | LDLIBS += -lavcodec -lavdevice -lavfilter -lavformat \
|
| | | -lavutil -lswresample -lswscale
|
| | | LDLIBS += -lcrypto -lssl -lpthread -ldl -lrt -lm
|
| | |
|
| | | CFLAGS += -fPIC
|
| | |
|
| | | DIRS_TEST = test/probe_test test/ptz_test |
| | | DIRS_TEST = test/probe_test test/ptz_test test/av_test
|
| | |
|
| | | %.o: $(SOURCES_CORE)/%.cpp $(SOURCES_SRVS)/%.cpp $(SOURCES_COMM)/%.cpp
|
| | | @echo " CPP " $@;
|
| | |
| | |
|
| | | #include <stdio.h>
|
| | | #include <stdlib.h>
|
| | | #include <assert.h>
|
| | | #include <time.h>
|
| | | #include <signal.h>
|
| | |
|
| | | #include "proto_comm.h"
|
| | | #include "proto_dbg.h"
|
| | |
|
| | | int timer_init(timer_t *timer_index, void (*timer_handler)(union sigval para)) {
|
| | | struct sigevent event;
|
| | | timer_t timer;
|
| | | int ret; |
| | |
|
| | | memset(&event, 0x00, sizeof(event));
|
| | | event.sigev_value.sival_int = ENABLE;
|
| | | event.sigev_value.sival_ptr = NULL;
|
| | | event.sigev_notify = SIGEV_THREAD;
|
| | | event.sigev_notify_function = timer_handler;
|
| | | |
| | | ret = timer_create(CLOCK_REALTIME, &event, &timer);
|
| | | if (ret) {
|
| | | return -1;
|
| | | }
|
| | |
|
| | | if (timer_index != NULL) {
|
| | | *timer_index = timer;
|
| | | }
|
| | |
|
| | | return 0;
|
| | | }
|
| | |
|
| | | int timer_start(timer_t timer_index, int sec) {
|
| | | int ret; |
| | | struct itimerspec ts;
|
| | |
|
| | | ts.it_interval.tv_sec = 0; |
| | | ts.it_interval.tv_nsec = 0; |
| | | ts.it_value.tv_sec = sec; |
| | | ts.it_value.tv_nsec = 0; |
| | | ret = timer_settime(timer_index, 0, &ts, NULL);
|
| | | if (ret) {
|
| | | return -1;
|
| | | }
|
| | |
|
| | | return ret; |
| | | }
|
| | |
|
| | | int timer_stop(timer_t timer_index) {
|
| | |
|
| | | int ret = timer_start(timer_index, 0);
|
| | |
|
| | | return ret;
|
| | | }
|
| | |
|
| | | int timer_destroy(timer_t timer_index) {
|
| | | int ret;
|
| | |
|
| | | ret = timer_delete(timer_index);
|
| | |
|
| | | return ret;
|
| | | }
|
| | |
|
| | | void soap_perror(struct soap *soap, const char *str)
|
| | | {
|
| | | if (NULL == str) {
|
| | | SOAP_DBGERR("[soap] error: %d, %s, %s\n", soap->error, *soap_faultcode(soap), *soap_faultstring(soap));
|
| | | } else {
|
| | | SOAP_DBGERR("[soap] %s error: %d, %s, %s\n", str, soap->error, *soap_faultcode(soap), *soap_faultstring(soap));
|
| | | }
|
| | | return;
|
| | | if (NULL == str) {
|
| | | SOAP_DBGERR("[soap] error: %d, %s, %s\n", soap->error, *soap_faultcode(soap), *soap_faultstring(soap));
|
| | | } else {
|
| | | SOAP_DBGERR("[soap] %s error: %d, %s, %s\n", str, soap->error, *soap_faultcode(soap), *soap_faultstring(soap));
|
| | | }
|
| | | |
| | | return;
|
| | | }
|
| | |
|
| | | void* proto_soap_malloc(struct soap *soap, unsigned int n)
|
| | | {
|
| | | void *p = NULL;
|
| | | void *p = NULL;
|
| | |
|
| | | if (n > 0) {
|
| | | p = soap_malloc(soap, n);
|
| | | SOAP_ASSERT(NULL != p);
|
| | | memset(p, 0x00 ,n);
|
| | | }
|
| | | return p;
|
| | | if (n > 0) {
|
| | | p = soap_malloc(soap, n);
|
| | | SOAP_ASSERT(NULL != p);
|
| | | memset(p, 0x00 ,n);
|
| | | }
|
| | | |
| | | return p;
|
| | | }
|
| | |
|
| | | struct soap *proto_soap_new(int timeout)
|
| | | {
|
| | | struct soap *soap = NULL; // soap环境变量
|
| | | struct soap *soap = NULL;
|
| | |
|
| | | SOAP_ASSERT(NULL != (soap = soap_new()));
|
| | | SOAP_ASSERT(NULL != (soap = soap_new()));
|
| | |
|
| | | soap_set_namespaces(soap, namespaces); // 设置soap的namespaces
|
| | | soap->recv_timeout = timeout; |
| | | soap->send_timeout = timeout;
|
| | | soap->connect_timeout = timeout;
|
| | | soap_set_namespaces(soap, namespaces);
|
| | | soap->recv_timeout = timeout; |
| | | soap->send_timeout = timeout;
|
| | | soap->connect_timeout = timeout;
|
| | |
|
| | | #if defined(__linux__) || defined(__linux)
|
| | | soap->socket_flags = MSG_NOSIGNAL; |
| | | soap->socket_flags = MSG_NOSIGNAL; |
| | | #endif
|
| | |
|
| | | soap_set_mode(soap, SOAP_C_UTFSTRING); |
| | | soap_set_mode(soap, SOAP_C_UTFSTRING); |
| | |
|
| | | return soap;
|
| | | return soap;
|
| | | }
|
| | |
|
| | | void proto_soap_delete(struct soap *soap)
|
| | | {
|
| | | soap_destroy(soap); // remove deserialized class instances (C++ only)
|
| | | soap_end(soap); // Clean up deserialized data (except class instances) and temporary data
|
| | | soap_done(soap); // Reset, close communications, and remove callbacks
|
| | | soap_free(soap); // Reset and deallocate the context created with soap_new or soap_copy
|
| | | soap_destroy(soap); // remove deserialized class instances (C++ only)
|
| | | soap_end(soap); // Clean up deserialized data (except class instances) and temporary data
|
| | | soap_done(soap); // Reset, close communications, and remove callbacks
|
| | | soap_free(soap); // Reset and deallocate the context created with soap_new or soap_copy
|
| | | }
|
| | |
|
| | | int proto_SetAuthInfo(struct soap *soap, const char *username, const char *password)
|
| | | {
|
| | | int result = 0;
|
| | | int result = 0;
|
| | |
|
| | | SOAP_ASSERT(NULL != username);
|
| | | SOAP_ASSERT(NULL != password);
|
| | | SOAP_ASSERT(NULL != username);
|
| | | SOAP_ASSERT(NULL != password);
|
| | |
|
| | | result = soap_wsse_add_UsernameTokenDigest(soap, NULL, username, password);
|
| | | SOAP_CHECK_ERROR(result, soap, "add_UsernameTokenDigest");
|
| | | result = soap_wsse_add_UsernameTokenDigest(soap, NULL, username, password);
|
| | | SOAP_CHECK_ERROR(result, soap, "add_UsernameTokenDigest");
|
| | |
|
| | | EXIT:
|
| | |
|
| | | return result;
|
| | | return result;
|
| | | }
|
| | |
|
| | | float para_check(float data)
|
| | |
| | | return ret;
|
| | | }
|
| | |
|
| | | /************************************************************************
|
| | | *初始化soap描述消息头
|
| | |
|
| | | *在本函数内部通过proto_soap_malloc分配的内存,将在proto_soap_delete中被释放
|
| | | ************************************************************************/
|
| | | void proto_init_header(struct soap *soap)
|
| | | {
|
| | | struct SOAP_ENV__Header *header = NULL;
|
| | |
| | | return;
|
| | | }
|
| | |
|
| | | /************************************************************************
|
| | | *初始化探测设备的范围和类型
|
| | |
|
| | | *在本函数内部通过proto_soap_malloc分配的内存,将在proto_soap_delete中被释放
|
| | | ************************************************************************/
|
| | | void proto_init_ProbeType(struct soap *soap, struct wsdd__ProbeType *probe)
|
| | | {
|
| | | struct wsdd__ScopesType *scope = NULL; // 用于描述查找哪类的Web服务
|
| | | struct wsdd__ScopesType *scope = NULL;
|
| | |
|
| | | SOAP_ASSERT(NULL != soap);
|
| | | SOAP_ASSERT(NULL != probe);
|
| | |
|
| | | scope = (struct wsdd__ScopesType *)proto_soap_malloc(soap, sizeof(struct wsdd__ScopesType));
|
| | | soap_default_wsdd__ScopesType(soap, scope); // 设置寻找设备的范围
|
| | | soap_default_wsdd__ScopesType(soap, scope);
|
| | | scope->__item = (char*)proto_soap_malloc(soap, strlen(SOAP_ITEM) + 1);
|
| | | strcpy(scope->__item, SOAP_ITEM);
|
| | |
|
| | | memset(probe, 0x00, sizeof(struct wsdd__ProbeType));
|
| | | soap_default_wsdd__ProbeType(soap, probe);
|
| | | probe->Scopes = scope;
|
| | | probe->Types = (char*)proto_soap_malloc(soap, strlen(SOAP_TYPES) + 1); // 设置寻找设备的类型
|
| | | probe->Types = (char*)proto_soap_malloc(soap, strlen(SOAP_TYPES) + 1);
|
| | | strcpy(probe->Types, SOAP_TYPES);
|
| | |
|
| | | return;
|
| | |
| | | *rtsp://100.100.100.140:554/av0_0
|
| | | *rtsp://username:password@100.100.100.140:554/av0_0
|
| | | ************************************************************************/
|
| | | int make_uri_withauth(char *src_uri, char *username, char *password, char *dest_uri, unsigned int size_dest_uri)
|
| | | int bridge_uri(char *src_uri, const char *username, const char *password, char *dest_uri, unsigned int size_dest_uri)
|
| | | {
|
| | | int result = 0;
|
| | | unsigned int needBufSize = 0;
|
| | |
| | | SOAP_ASSERT(NULL != dest_uri);
|
| | | memset(dest_uri, 0x00, size_dest_uri);
|
| | |
|
| | | needBufSize = strlen(src_uri) + strlen(username) + strlen(password) + 3; // 检查缓存是否足够,包括‘:’和‘@’和字符串结束符
|
| | | needBufSize = strlen(src_uri) + strlen(username) + strlen(password) + 3; //check buf size with character ‘:’ and ‘@'
|
| | | if (size_dest_uri < needBufSize) {
|
| | | SOAP_DBGERR("dest uri buf size is not enough.\n");
|
| | | result = -1;
|
| | | goto EXIT;
|
| | | }
|
| | |
|
| | | if (0 == strlen(username) && 0 == strlen(password)) { // 生成新的uri地址
|
| | | if (0 == strlen(username) && 0 == strlen(password)) {
|
| | | strcpy(dest_uri, src_uri);
|
| | | } else {
|
| | | char *p = strstr(src_uri, "//");
|
| | |
| | | #include <stdio.h>
|
| | | #include <stdlib.h>
|
| | | #include <assert.h>
|
| | | #include <time.h>
|
| | | #include <signal.h>
|
| | |
|
| | | #include "soapH.h"
|
| | | #include "soapStub.h"
|
| | | #include "wsaapi.h"
|
| | |
| | | #define min(a,b) (((a) < (b)) ? (a) : (b))
|
| | | #endif
|
| | |
|
| | | #define WT_TIME 5
|
| | | #define STOP_WT_TIME 3
|
| | | #define WT_MAX_TIME (60 * 20)
|
| | |
|
| | | #define SOAP_ASSERT assert
|
| | | #define SOAP_DBGERR printf
|
| | |
|
| | |
| | | #define SOAP_DBGLOG
|
| | | #endif
|
| | |
|
| | | #define USERNAME "On_admin" |
| | | #define PASSWORD "a12345678"
|
| | |
|
| | | #define SOAP_TO "urn:schemas-xmlsoap-org:ws:2005:04:discovery"
|
| | | #define SOAP_ACTION "http://schemas.xmlsoap.org/ws/2005/04/discovery/Probe"
|
| | |
|
| | | #define SOAP_MCAST_ADDR "soap.udp://239.255.255.250:3702"
|
| | |
|
| | | #define SOAP_ITEM "" // 寻找的设备范围
|
| | | #define SOAP_TYPES "dn:NetworkVideoTransmitter" // 寻找的设备类型
|
| | | #define SOAP_ITEM ""
|
| | | #define SOAP_TYPES "dn:NetworkVideoTransmitter" //device type
|
| | |
|
| | | #define ADDR_PREFIX "http://"
|
| | | #define ADDR_LAST "/"
|
| | |
|
| | | #define NAME_BRIDGE "_"
|
| | | #define NAME_DOT "."
|
| | | #define NAME_MID "-"
|
| | |
|
| | | #define SOAP_SOCK_TIMEOUT (10) //sec
|
| | |
|
| | | #define TRUE 1
|
| | | #define FALSE 0
|
| | |
|
| | | #define ENABLE 0
|
| | | #define DISABLE 1
|
| | |
|
| | | #define PARA_MIN (-1)
|
| | | #define PARA_MAX (1)
|
| | |
|
| | | #define PROTO_ADDRESS_SIZE (128) // URI地址长度
|
| | | #define PROTO_TOKEN_SIZE (65) // token长度
|
| | | #define PROTO_ADDRESS_SIZE (128)
|
| | | #define PROTO_TOKEN_SIZE (65) //token size
|
| | | #define PTOTO_ADDRESS_ADD (65)
|
| | |
|
| | | /* 视频编码器配置信息 */
|
| | | #define MAX_BUF_SIZE 600
|
| | |
|
| | | /*video encoder configurations */
|
| | | struct tagVideoEncoderConfiguration
|
| | | {
|
| | | char token[PROTO_TOKEN_SIZE]; // 唯一标识该视频编码器的令牌字符串
|
| | | int Width; // 分辨率
|
| | | char token[PROTO_TOKEN_SIZE]; //video token
|
| | | int Width; //resolution
|
| | | int Height;
|
| | | };
|
| | |
|
| | |
| | | } \
|
| | | } while (0)
|
| | |
|
| | | int timer_init(timer_t *timer_index, void (*timer_handler)(union sigval para));
|
| | | int timer_start(timer_t timer_index, int sec);
|
| | | int timer_stop(timer_t timer_index);
|
| | | int timer_destroy(timer_t timer_index);
|
| | |
|
| | | void soap_perror(struct soap *soap, const char *str);
|
| | | void * proto_soap_malloc(struct soap *soap, unsigned int n);
|
| | |
| | | void proto_init_ProbeType(struct soap *soap, struct wsdd__ProbeType *probe);
|
| | | float para_check(float data);
|
| | |
|
| | | int make_uri_withauth(char *src_uri, char *username, char *password, char *dest_uri, unsigned int size_dest_uri);
|
| | | int bridge_uri(char *src_uri, const char *username, const char *password, char *dest_uri, unsigned int size_dest_uri);
|
| | | int soap_wsse_add_UsernameTokenDigest(struct soap *soap, const char *id, const char *username, const char *password);
|
| | |
|
| | | int proto_GetDeviceInformation(const char *DeviceXAddr, const char *username, const char *passwd);
|
| | |
| | | };
|
| | |
|
| | | #ifdef PROTO_DEBUG
|
| | |
|
| | | void dump__wsdd__ProbeMatches(struct __wsdd__ProbeMatches *rep);
|
| | | void dump__GetPresetsResponse(struct _tptz__GetPresetsResponse *rep);
|
| | | void dump_tds__GetCapabilitiesResponse(struct _tds__GetCapabilitiesResponse *rep);
|
| | |
| | | void dump_trt__GetVideoEncoderConfigurationOptionsResponse(struct _trt__GetVideoEncoderConfigurationOptionsResponse *rep);
|
| | | void log_level_val(unsigned int level, const char *prestr, enum LOG_TYPE type, const void *val);
|
| | | #else
|
| | |
|
| | | #define dump__wsdd__ProbeMatches
|
| | | #define dump_tds__GetCapabilitiesResponse
|
| | | #define dump_tds__GetDeviceInformationResponse
|
| | |
| | | #define dump_trt__GetVideoEncoderConfigurationsResponse
|
| | | #define dump_trt__GetCompatibleVideoEncoderConfigurationsResponse
|
| | | #define dump_trt__GetVideoEncoderConfigurationOptionsResponse
|
| | | #define log_level_val
|
| | |
|
| | | #endif
|
| | |
|
| New file |
| | |
| | | #include <stdio.h>
|
| | | #include <stdlib.h>
|
| | | #include <assert.h>
|
| | | #include <errno.h>
|
| | | #include <sys/types.h>
|
| | | #include <unistd.h>
|
| | | #include <signal.h>
|
| | | #include <sys/wait.h>
|
| | | #include <time.h>
|
| | | #include <sys/vfs.h>
|
| | | #include <stdint.h>
|
| | | #include <sys/stat.h>
|
| | | #include <signal.h>
|
| | | #include <sys/types.h>
|
| | | #include <dirent.h>
|
| | |
|
| | | #include "libavcodec/avcodec.h"
|
| | | #include "libavdevice/avdevice.h"
|
| | | #include "libavformat/avformat.h"
|
| | | #include "libavfilter/avfilter.h"
|
| | | #include "libavutil/avutil.h"
|
| | | #include "libswscale/swscale.h"
|
| | | #include "libavutil/pixdesc.h"
|
| | |
|
| | | #include "probe/probe.h"
|
| | | #include "av_demux/av_demux.h"
|
| | | #include "proto_comm.h"
|
| | | #include "proto_dbg.h"
|
| | |
|
| | | static AVDevs *gAVDevs = NULL;
|
| | |
|
| | | static int data_cmp(char *s1, char *s2, char *dlim);
|
| | |
|
| | | /*signal process interrupt handler*/
|
| | | static void handler(int sig) |
| | | {
|
| | | sync();
|
| | | }
|
| | |
|
| | | void av_timer_handler(union sigval para) |
| | | {
|
| | | gAVDevs->slice_stat = FALSE; |
| | | }
|
| | |
|
| | | /*parse the location to get the right direction*/
|
| | | static int get_dir_with_key(char *dir_path, char *name, char *key, char *buf, int length) {
|
| | | DIR *pDir;
|
| | | char *ptr;
|
| | | char temp = 0;
|
| | | char found = FALSE;
|
| | | struct dirent * entry;
|
| | | char parse_buf[MAX_BUF_SIZE] = { 0x00 };
|
| | |
|
| | | pDir = opendir(dir_path);
|
| | | if ( |
| | | pDir == NULL) {
|
| | | SOAP_DBGERR("the path(%s) can not be opened!\n", dir_path);
|
| | |
|
| | | return -1; |
| | | }
|
| | |
|
| | | while((entry = readdir(pDir)) != NULL) { |
| | |
|
| | | if (entry->d_type & DT_DIR) {
|
| | |
|
| | | if ((strcmp(entry->d_name, ".") != 0) && (strcmp(entry->d_name, "..") != 0)) { |
| | |
|
| | | ptr = strstr(entry->d_name, NAME_BRIDGE);
|
| | | |
| | | if ((ptr != NULL) && (strcmp(ptr + 1, name) == 0)) {
|
| | | |
| | | if (data_cmp(entry->d_name, key, NAME_MID) <= 0) {
|
| | | |
| | | found = TRUE;
|
| | | if (temp == 0) {
|
| | | memcpy(parse_buf, entry->d_name, sizeof(parse_buf));
|
| | |
|
| | | temp = 1;
|
| | |
|
| | | } else {
|
| | | |
| | | if (data_cmp(parse_buf, entry->d_name, NAME_MID) < 0) {
|
| | | memset(parse_buf, 0x00, sizeof(parse_buf));
|
| | | memcpy(parse_buf, entry->d_name, sizeof(parse_buf));
|
| | | }
|
| | | }
|
| | | }
|
| | | }
|
| | | } |
| | | }
|
| | | }
|
| | |
|
| | | closedir(pDir);
|
| | |
|
| | | if (found == TRUE) {
|
| | | memcpy(buf, dir_path, length - 1);
|
| | | memcpy(buf + strlen(buf), "/", length - strlen(buf) - 1);
|
| | | memcpy(buf + strlen(buf), parse_buf, length - strlen(buf) - 1);
|
| | | } else {
|
| | | buf[0] = 0;
|
| | | }
|
| | |
|
| | | return found;
|
| | | }
|
| | |
|
| | | int playback_get_key(playback_key set, char *buf, int length) {
|
| | | int ret;
|
| | | char parse_buf[MAX_BUF_SIZE] = { 0x00 };
|
| | | char buf_temp[MAX_BUF_SIZE] = { 0x00 };
|
| | |
|
| | | if ((set.name == NULL) || (set.date == NULL) || (set.time == NULL)) {
|
| | | SOAP_DBGERR("invalid playbeck key set parameters!\n");
|
| | |
|
| | | return 0;
|
| | | }
|
| | |
|
| | | ret = get_dir_with_key(VIDEO_PUT_DIR, set.name, set.date, parse_buf, sizeof(parse_buf));
|
| | | if (ret > 0) {
|
| | | ret = get_file_with_key(parse_buf, set.time, buf_temp, sizeof(buf_temp), 0);
|
| | | if (ret > 0) {
|
| | | memcpy(buf, buf_temp, length);
|
| | | }
|
| | | }
|
| | |
|
| | | return ret;
|
| | | }
|
| | |
|
| | | static int get_dir_oldest(char *dir_path, char *buf, int length) {
|
| | | DIR *pDir;
|
| | | char temp = 0;
|
| | | int found = FALSE;
|
| | | struct dirent * entry;
|
| | | char parse_buf[MAX_BUF_SIZE] = { 0x00 };
|
| | |
|
| | | pDir = opendir(dir_path);
|
| | | if ( |
| | | pDir == NULL) {
|
| | | SOAP_DBGERR("the path(%s) can not be opened!\n", dir_path);
|
| | |
|
| | | return -1; |
| | | }
|
| | |
|
| | | while((entry = readdir(pDir)) != NULL) { |
| | |
|
| | | if (entry->d_type & DT_DIR) {
|
| | |
|
| | | if ((strcmp(entry->d_name, ".") != 0) && (strcmp(entry->d_name, "..") != 0)) { |
| | |
|
| | | found = TRUE;
|
| | | if (temp == 0) {
|
| | | memcpy(parse_buf, entry->d_name, sizeof(parse_buf));
|
| | |
|
| | | temp = 1;
|
| | |
|
| | | } else {
|
| | |
|
| | | if (data_cmp(parse_buf, entry->d_name, NAME_MID) > 0) {
|
| | | memset(parse_buf, 0x00, sizeof(parse_buf));
|
| | | memcpy(parse_buf, entry->d_name, sizeof(parse_buf));
|
| | | }
|
| | | }
|
| | | }
|
| | | }
|
| | | }
|
| | |
|
| | | closedir(pDir);
|
| | |
|
| | | if (found == TRUE) {
|
| | | memcpy(buf, dir_path, length);
|
| | | memcpy(buf + strlen(buf), "/", length - strlen(buf) - 1);
|
| | | memcpy(buf + strlen(buf), parse_buf, length - strlen(buf) - 1);
|
| | |
|
| | | return 0;
|
| | | }
|
| | |
|
| | | buf[0] = 0x00;
|
| | |
|
| | | return -1;
|
| | | }
|
| | |
|
| | | /*parse the location to get the right file.
|
| | | * flag - include the key itself or not
|
| | | */
|
| | | static int get_file_with_key(char *dir_path, char *key, char *buf, int length, int flag) {
|
| | | DIR *pDir;
|
| | | char temp = 0;
|
| | | char found = FALSE;
|
| | | char found_flag = FALSE;
|
| | | struct dirent * entry;
|
| | | char parse_buf[MAX_BUF_SIZE] = { 0x00 };
|
| | |
|
| | | pDir = opendir(dir_path);
|
| | | if (pDir == NULL) {
|
| | | SOAP_DBGERR("the path(%s) can not be opened!\n", dir_path);
|
| | |
|
| | | return -1;
|
| | | }
|
| | |
|
| | | while((entry = readdir(pDir)) != NULL) {
|
| | |
|
| | | if (entry->d_type & DT_REG) {
|
| | |
|
| | | if ((key != NULL) && (data_cmp(key, entry->d_name, NAME_MID) >= 0)) {
|
| | |
|
| | | if ((flag == 1) && (data_cmp(key, entry->d_name, NAME_MID) > 0)) {
|
| | | found = TRUE;
|
| | | } else if (flag == 0) {
|
| | | found = TRUE;
|
| | | }
|
| | | } else if (key == NULL) {
|
| | | found = TRUE;
|
| | | }
|
| | |
|
| | | if (found == TRUE) {
|
| | |
|
| | | found_flag = TRUE;
|
| | |
|
| | | if (temp == 0) {
|
| | | memcpy(parse_buf, entry->d_name, sizeof(parse_buf));
|
| | |
|
| | | temp = 1;
|
| | |
|
| | | } else {
|
| | |
|
| | | if (data_cmp(parse_buf, entry->d_name, NAME_MID) < 0) {
|
| | | memset(parse_buf, 0x00, sizeof(parse_buf));
|
| | | memcpy(parse_buf, entry->d_name, sizeof(parse_buf));
|
| | | }
|
| | | }
|
| | |
|
| | | found = FALSE;
|
| | | }
|
| | | }
|
| | | }
|
| | |
|
| | | closedir(pDir);
|
| | |
|
| | | if (found_flag == TRUE) {
|
| | | memcpy(buf, dir_path, length - 1);
|
| | | memcpy(buf + strlen(buf), "/", length - strlen(buf) - 1);
|
| | | memcpy(buf + strlen(buf), parse_buf, length - strlen(buf) - 1);
|
| | | } else {
|
| | | buf[0] = 0;
|
| | | }
|
| | |
|
| | | return found_flag;
|
| | | }
|
| | |
|
| | | /*compare the string between s1 and s2*/
|
| | | static int data_cmp(char *s1, char *s2, char *dlim)
|
| | | {
|
| | | int data1;
|
| | | int data2;
|
| | | char *ptr1;
|
| | | char *ptr2;
|
| | |
|
| | | data1 = atoi(s1);
|
| | | data2 = atoi(s2);
|
| | | if (data1 > data2)
|
| | | return 1;
|
| | |
|
| | | if (data1 < data2)
|
| | | return -1;
|
| | |
|
| | | ptr1 = strstr(s1, dlim);
|
| | | ptr2 = strstr(s2, dlim);
|
| | | data1 = atoi(ptr1 + 1);
|
| | | data2 = atoi(ptr2 + 1);
|
| | | if (data1 > data2)
|
| | | return 1;
|
| | |
|
| | | if (data1 < data2)
|
| | | return -1;
|
| | |
|
| | | ptr1 = strstr(ptr1 + 1, dlim);
|
| | | ptr2 = strstr(ptr2 + 1, dlim);
|
| | | data1 = atoi(ptr1 + 1);
|
| | | data2 = atoi(ptr2 + 1);
|
| | | if (data1 > data2)
|
| | | return 1;
|
| | |
|
| | | if (data1 < data2)
|
| | | return -1;
|
| | |
|
| | | return 0;
|
| | | }
|
| | |
|
| | | /*av stream capture task*/
|
| | | static void *task_av_capture(void *arg) |
| | | {
|
| | | struct timespec time_exp;
|
| | |
|
| | | time_exp.tv_sec = WT_TIME;
|
| | | time_exp.tv_nsec = 0; |
| | | //int data = *(int *)arg;
|
| | | |
| | | pthread_detach(pthread_self());
|
| | |
|
| | | while(1) {
|
| | | sem_timedwait(&(gAVDevs->sem_cap), &time_exp);
|
| | |
|
| | | while(gAVDevs->run_stat == TRUE) {
|
| | |
|
| | | av_start_cap(gAVDevs);
|
| | | |
| | | gAVDevs->slice_stat = TRUE;
|
| | | |
| | | }
|
| | |
|
| | | if (gAVDevs->dev_stat == DISABLE) {
|
| | | |
| | | gAVDevs->proc_stat = DISABLE;
|
| | | |
| | | }
|
| | | }
|
| | |
|
| | | return 0;
|
| | | }
|
| | |
|
| | | /*monitor the disk usage*/
|
| | | static void *task_disk_mon(void *arg)
|
| | | {
|
| | | int ret;
|
| | | uint64_t blocksize;
|
| | | uint64_t totalsize;
|
| | | uint64_t availableDisk;
|
| | | struct statfs diskInfo; |
| | | char buf[MAX_BUF_SIZE] = { 0x00 };
|
| | | char buf_cmd[MAX_BUF_SIZE] = { 0x00 };
|
| | |
|
| | | pthread_detach(pthread_self());
|
| | |
|
| | | while(1) {
|
| | | statfs(VIDEO_PUT_DIR, &diskInfo);
|
| | |
|
| | | blocksize = diskInfo.f_bsize;
|
| | | totalsize = blocksize * diskInfo.f_blocks;
|
| | | availableDisk = diskInfo.f_bavail * blocksize;
|
| | |
|
| | | while ((availableDisk * 1.0 / totalsize) < DISK_FREE_THRES) {
|
| | | ret = get_dir_oldest(VIDEO_PUT_DIR, buf, sizeof(buf));
|
| | | if (ret == 0) {
|
| | | memcpy(buf_cmd, "rm -rf ", sizeof(buf_cmd));
|
| | | snprintf(buf_cmd + strlen(buf_cmd), sizeof(buf_cmd) - strlen(buf_cmd) - 1, "rm -rf %s", buf);
|
| | | system(buf_cmd);
|
| | | sleep(WT_TIME);
|
| | |
|
| | | statfs(VIDEO_PUT_DIR, &diskInfo);
|
| | |
|
| | | blocksize = diskInfo.f_bsize;
|
| | | totalsize = blocksize * diskInfo.f_blocks;
|
| | | availableDisk = diskInfo.f_bavail * blocksize;
|
| | |
|
| | | memset(buf, 0x00, sizeof(buf));
|
| | | memset(buf_cmd, 0x00, sizeof(buf_cmd));
|
| | | } else {
|
| | | |
| | | break;
|
| | | }
|
| | | }
|
| | |
|
| | | sleep(WT_MAX_TIME);
|
| | | }
|
| | |
|
| | | return NULL;
|
| | | }
|
| | |
|
| | | /*initialize the stream data channel*/
|
| | | int proto_AVInit(void) {
|
| | |
|
| | | int ret; |
| | | int flag;
|
| | | pthread_t tid;
|
| | | struct stat stat_buf;
|
| | |
|
| | | if (stat(VIDEO_CONF_DATA, &stat_buf) != 0) {
|
| | | SOAP_DBGERR("The video configuration(%s) is not existed! Please put it firstly!\n", VIDEO_CONF_DATA);
|
| | |
|
| | | return -1;
|
| | | }
|
| | |
|
| | | ret = chmod(VIDEO_CONF_DATA, 0777);
|
| | | if (ret < 0) {
|
| | | SOAP_DBGERR("parse the configuration error: %s\n", strerror(errno));
|
| | |
|
| | | return -1;
|
| | | }
|
| | |
|
| | | ret = DiscoverDevice(cb_av_probe);
|
| | | if (ret <= 0) { |
| | | return -1;
|
| | | }
|
| | |
|
| | | ret = pthread_create(&tid, NULL, task_av_capture, &flag);
|
| | | if (ret) {
|
| | | return -1;
|
| | | }
|
| | |
|
| | | ret = pthread_create(&tid, NULL, task_disk_mon, &flag);
|
| | | if (ret) {
|
| | | return -1;
|
| | | }
|
| | |
|
| | | return 0;
|
| | | }
|
| | |
|
| | | void proto_AVStart(AVDevs *DevData) {
|
| | | |
| | | DevData->slice_stat = TRUE;
|
| | | |
| | | DevData->run_stat = TRUE;
|
| | |
|
| | | sem_post(&(DevData->sem_cap));
|
| | |
|
| | | }
|
| | | |
| | | static int av_start_cap(AVDevs *DevData) {
|
| | | int ret;
|
| | | pid_t pid;
|
| | | char data_buf[MAX_BUF_SIZE] = { 0x00 };
|
| | | char temp_buf[MAX_BUF_SIZE] = { 0x00 };
|
| | | char data_buf_temp[MAX_BUF_SIZE] = { 0x00 };
|
| | | char buf[MAX_BUF_SIZE] = { 0x00 };
|
| | |
|
| | | signal(SIGINT, handler);
|
| | |
|
| | | pid = fork();
|
| | | if (pid < 0) {
|
| | | SOAP_DBGERR("AV start failure: fork failed!\n");
|
| | |
|
| | | return -1;
|
| | |
|
| | | }
|
| | |
|
| | | if (pid > 0) {
|
| | |
|
| | | timer_start(gAVDevs->timer_id, gAVDevs->timer_sec);
|
| | |
|
| | | while((gAVDevs->run_stat == TRUE) && (gAVDevs->slice_stat == TRUE)) {
|
| | | sleep(1);
|
| | | }
|
| | | timer_stop(gAVDevs->timer_id);
|
| | |
|
| | | kill(pid, SIGINT);
|
| | |
|
| | | wait(NULL);
|
| | |
|
| | | sync();
|
| | |
|
| | | if ((gAVDevs->work_mode == PAUSE) && (gAVDevs->pause_enable == FALSE)) {
|
| | | |
| | | gAVDevs->pause_enable = TRUE;
|
| | |
|
| | | } else if ((gAVDevs->work_mode == PAUSE) && (gAVDevs->pause_enable == TRUE)) {
|
| | |
|
| | | system_date_get(data_buf_temp, sizeof(data_buf_temp));
|
| | |
|
| | | ret = get_dir_with_key(VIDEO_PUT_DIR, gAVDevs->ip, data_buf_temp, data_buf, sizeof(data_buf));
|
| | | if (ret > 0) {
|
| | |
|
| | | memcpy(temp_buf, data_buf, sizeof(temp_buf) - 1);
|
| | | memset(data_buf, 0x00, sizeof(data_buf));
|
| | | get_file_with_key(temp_buf, NULL, data_buf, sizeof(data_buf), 0);
|
| | |
|
| | | memset(data_buf_temp, 0x00, sizeof(data_buf_temp));
|
| | | get_file_with_key(temp_buf, data_buf, data_buf_temp, sizeof(data_buf_temp), 1); |
| | |
|
| | | snprintf(buf, sizeof(buf) - 1, "%s", VIDEO_CONF_DATA);
|
| | | snprintf(buf + strlen(buf), sizeof(buf) - strlen(buf) - 1, "%s %s", data_buf_temp, data_buf);
|
| | | system(buf);
|
| | | }
|
| | |
|
| | | gAVDevs->work_mode = NORMAL;
|
| | |
|
| | | gAVDevs->pause_enable = FALSE;
|
| | | }
|
| | |
|
| | | } else {
|
| | |
|
| | | ret = video_file_create(data_buf, sizeof(data_buf));
|
| | | if (ret < 0) {
|
| | | return 0;
|
| | | }
|
| | |
|
| | | ret = execl(FFMPEG_BIN_DIR, "ffmpeg", "-f", "rtsp", "-rtsp_transport", "tcp", "-i", gAVDevs->uri_data, "-vcodec", "copy", "-y", data_buf, (char *)NULL);
|
| | | if (ret < 0) {
|
| | | SOAP_DBGERR("ffmpeg stuffs are not available: %s\n", strerror(errno));
|
| | | SOAP_DBGERR("please check and confirm it had already been installed correctly!\n");
|
| | | }
|
| | | |
| | | }
|
| | |
|
| | | return 0;
|
| | | }
|
| | |
|
| | | void proto_AVStop(AVDevs *DevData, enum wr_mode mode) {
|
| | |
|
| | | DevData->run_stat = FALSE;
|
| | |
|
| | | DevData->work_mode = mode;
|
| | | }
|
| | |
|
| | | static int video_file_create(char *data_buf, int length) {
|
| | | |
| | | int ret;
|
| | | int len;
|
| | | struct stat stat_buf;
|
| | | char buf[MAX_BUF_SIZE] = { 0x00 };
|
| | |
|
| | | struct tm tloc;
|
| | | time_t now;
|
| | | time(&now);
|
| | | localtime_r(&now, &tloc);
|
| | |
|
| | | if (stat(VIDEO_PUT_DIR, &stat_buf) != 0) {
|
| | | memcpy(buf, "mkdir -p ", sizeof(buf));
|
| | | snprintf(buf + strlen(buf), sizeof(buf) - strlen(buf) - 1, "%s", VIDEO_PUT_DIR);
|
| | | system(buf);
|
| | | }
|
| | |
|
| | | memset(buf, 0x00, sizeof(buf));
|
| | | len = MAX_BUF_SIZE - 1;
|
| | | snprintf(buf, len, "%s", VIDEO_PUT_DIR);
|
| | | len = (MAX_BUF_SIZE - 1) >= strlen(buf) ? MAX_BUF_SIZE - 1 - strlen(buf) : 0;
|
| | | snprintf(buf + strlen(buf), len, "/%d-", tloc.tm_year + 1900);
|
| | | len = (MAX_BUF_SIZE - 1) >= strlen(buf) ? MAX_BUF_SIZE - 1 - strlen(buf) : 0;
|
| | | snprintf(buf + strlen(buf), len, "%d-", tloc.tm_mon + 1);
|
| | | len = (MAX_BUF_SIZE - 1) >= strlen(buf) ? MAX_BUF_SIZE - 1 - strlen(buf) : 0;
|
| | | snprintf(buf + strlen(buf), len, "%d", tloc.tm_mday);
|
| | | len = (MAX_BUF_SIZE - 1) >= strlen(buf) ? MAX_BUF_SIZE - 1 - strlen(buf) : 0;
|
| | | snprintf(buf + strlen(buf), len, "_%s", gAVDevs->ip);
|
| | |
|
| | | if (stat(buf, &stat_buf) != 0) {
|
| | |
|
| | | ret = mkdir(buf, 0777);
|
| | | if (ret < 0) {
|
| | | SOAP_DBGERR("the video put dir create failure: %s\n", strerror(errno));
|
| | |
|
| | | return -1; |
| | | } |
| | | }
|
| | |
|
| | | time(&now);
|
| | | localtime_r(&now, &tloc);
|
| | | len = (MAX_BUF_SIZE - 1) >= strlen(buf) ? MAX_BUF_SIZE - 1 - strlen(buf) : 0;
|
| | | snprintf(buf + strlen(buf), len, "/%d-", tloc.tm_hour);
|
| | | len = (MAX_BUF_SIZE - 1) >= strlen(buf) ? MAX_BUF_SIZE - 1 - strlen(buf) : 0;
|
| | | snprintf(buf + strlen(buf), len, "%d-", tloc.tm_min);
|
| | | len = (MAX_BUF_SIZE - 1) >= strlen(buf) ? MAX_BUF_SIZE - 1 - strlen(buf) : 0;
|
| | | snprintf(buf + strlen(buf), len, "%d.mp4", tloc.tm_sec);
|
| | |
|
| | | memcpy(data_buf, buf, length);
|
| | |
|
| | | return 0;
|
| | | }
|
| | |
|
| | | static void system_date_get(char *buf, int len) |
| | | {
|
| | | struct tm tloc;
|
| | | time_t now;
|
| | | time(&now);
|
| | | localtime_r(&now, &tloc);
|
| | |
|
| | | sprintf(buf, "%d", tloc.tm_year + 1900);
|
| | | sprintf(buf + strlen(buf), "-%d", tloc.tm_mon + 1);
|
| | | sprintf(buf + strlen(buf), "-%d", tloc.tm_mday);
|
| | |
|
| | | return;
|
| | | }
|
| | |
|
| | | static void cb_av_probe(char *DeviceXAddr)
|
| | | {
|
| | | int ret;
|
| | | int len;
|
| | | char *pos_s, *pos_e;
|
| | |
|
| | | if (gAVDevs == NULL) {
|
| | |
|
| | | gAVDevs = malloc(sizeof(AVDevs));
|
| | |
|
| | | SOAP_ASSERT(gAVDevs != NULL);
|
| | | |
| | | memset(gAVDevs, 0x00, sizeof(AVDevs));
|
| | |
|
| | | pos_s = strstr(DeviceXAddr, ADDR_PREFIX);
|
| | | pos_e = strstr(DeviceXAddr + strlen(ADDR_PREFIX), ADDR_LAST);
|
| | | len = pos_e - DeviceXAddr - strlen(ADDR_PREFIX);
|
| | | memcpy(gAVDevs->ip, DeviceXAddr + strlen(ADDR_PREFIX), len);
|
| | |
|
| | | gAVDevs->timer_sec = VIDEO_DURATION;
|
| | | |
| | | gAVDevs->dev_stat = ENABLE;
|
| | | gAVDevs->run_stat = FALSE;
|
| | |
|
| | | ret = sem_init(&(gAVDevs->sem_cap), 0, 0);
|
| | | SOAP_ASSERT(ret == 0);
|
| | |
|
| | | timer_init(&(gAVDevs->timer_id), av_timer_handler);
|
| | | }
|
| | |
|
| | | /*Get the device capabilities*/
|
| | | proto_GetCapabilities(DeviceXAddr, &(gAVDevs->capa), USERNAME, PASSWORD);
|
| | |
|
| | | /*Parse the stream configurations*/
|
| | | proto_GetProfiles(gAVDevs->capa.MediaXAddr, &(gAVDevs->profiles), USERNAME, PASSWORD);
|
| | | |
| | | proto_GetStreamUri(gAVDevs->capa.MediaXAddr, gAVDevs->profiles->token, gAVDevs->uri, sizeof(gAVDevs->uri), USERNAME, PASSWORD);
|
| | |
|
| | | bridge_uri(gAVDevs->uri, USERNAME, PASSWORD, gAVDevs->uri_data, sizeof(gAVDevs->uri_data));
|
| | |
|
| | | }
|
| | |
|
| | | AVDevs *proto_AVGethandle(void) |
| | | {
|
| | | return gAVDevs;
|
| | | }
|
| | |
|
| | | void proto_AVClose(void) |
| | | {
|
| | | if (gAVDevs != NULL) {
|
| | |
|
| | | if (gAVDevs->dev_stat == ENABLE) {
|
| | | proto_AVStop(gAVDevs, NORMAL);
|
| | | } |
| | |
|
| | | gAVDevs->dev_stat = DISABLE;
|
| | |
|
| | | while(gAVDevs->proc_stat != DISABLE) {
|
| | | sleep(2);
|
| | | }
|
| | |
|
| | | sem_destroy(&(gAVDevs->sem_cap));
|
| | |
|
| | | timer_destroy(gAVDevs->timer_id);
|
| | |
|
| | | free(gAVDevs->profiles);
|
| | |
|
| | | free(gAVDevs);
|
| | |
|
| | | gAVDevs = NULL;
|
| | | }
|
| | | }
|
| | |
|
| | | /*get the video and audio packet*/
|
| | | void get_stream(AVDevs *DevData)
|
| | | {
|
| | | unsigned int i;
|
| | | int ret;
|
| | | int video_st_index = -1;
|
| | | int audio_st_index = -1;
|
| | | AVFormatContext *ifmt_ctx = NULL;
|
| | | AVPacket pkt;
|
| | | AVStream *st = NULL;
|
| | | char errbuf[64];
|
| | |
|
| | | /*Open the input file for reading*/
|
| | | if ((ret = avformat_open_input(&ifmt_ctx, DevData->uri_data, 0, NULL)) < 0) {
|
| | | SOAP_DBGERR("Could not open input file '%s' (error '%s')\n", DevData->uri_data, av_make_error_string(errbuf, sizeof(errbuf), ret));
|
| | | |
| | | goto EXIT;
|
| | | }
|
| | |
|
| | | /*Get information on the input file (number of streams etc.))*/
|
| | | if ((ret = avformat_find_stream_info(ifmt_ctx, NULL)) < 0) {
|
| | | SOAP_DBGERR("Could not open find stream info (error '%s')\n", av_make_error_string(errbuf, sizeof(errbuf), ret));
|
| | | |
| | | goto EXIT;
|
| | | }
|
| | |
|
| | | for (i = 0; i < ifmt_ctx->nb_streams; i++) {
|
| | | av_dump_format(ifmt_ctx, i, DevData->uri_data, 0);
|
| | | }
|
| | |
|
| | | /*find video stream index*/
|
| | | for (i = 0; i < ifmt_ctx->nb_streams; i++) {
|
| | | |
| | | st = ifmt_ctx->streams[i];
|
| | |
|
| | | switch(st->codec->codec_type) {
|
| | | |
| | | case AVMEDIA_TYPE_AUDIO: |
| | | audio_st_index = i; |
| | |
|
| | | break;
|
| | | |
| | | case AVMEDIA_TYPE_VIDEO: |
| | | video_st_index = i; |
| | |
|
| | | break;
|
| | | |
| | | default: |
| | | break;
|
| | | }
|
| | | }
|
| | | |
| | | if (-1 == video_st_index) {
|
| | | SOAP_DBGERR("No H.264 video stream in the input file\n");
|
| | | |
| | | goto EXIT;
|
| | | }
|
| | |
|
| | | /*initialize packet*/
|
| | | av_init_packet(&pkt);
|
| | | pkt.data = NULL;
|
| | | pkt.size = 0;
|
| | |
|
| | | while (1) {
|
| | | do {
|
| | | |
| | | ret = av_read_frame(ifmt_ctx, &pkt);
|
| | |
|
| | | } while (ret == AVERROR(EAGAIN));
|
| | |
|
| | | if (ret < 0) {
|
| | | SOAP_DBGERR("Could not read frame (error '%s')\n", av_make_error_string(errbuf, sizeof(errbuf), ret));
|
| | | |
| | | break;
|
| | | }
|
| | |
|
| | | /*video frame*/
|
| | | if (pkt.stream_index == video_st_index) {
|
| | | |
| | | SOAP_DBGERR("Video Packet size = %d\n", pkt.size);
|
| | | |
| | | } else if(pkt.stream_index == audio_st_index) {
|
| | | /*audio frame*/
|
| | | SOAP_DBGERR("Audio Packet size = %d\n", pkt.size);
|
| | |
|
| | | } else {
|
| | |
|
| | | SOAP_DBGERR("Unknow Packet size = %d\n", pkt.size);
|
| | | |
| | | }
|
| | |
|
| | | av_packet_unref(&pkt);
|
| | | }
|
| | |
|
| | | EXIT:
|
| | |
|
| | | if (NULL != ifmt_ctx) {
|
| | | |
| | | avformat_close_input(&ifmt_ctx);
|
| | | |
| | | ifmt_ctx = NULL;
|
| | | }
|
| | |
|
| | | return ;
|
| | | }
|
| | |
|
| | | /*Get the device service stream address*/
|
| | | int proto_GetStreamUri(const char *MediaXAddr, char *ProfileToken, char *uri, unsigned int sizeuri, const char *username, const char *passwd)
|
| | | {
|
| | |
|
| | | int result = 0;
|
| | | struct soap *soap = NULL;
|
| | | struct tt__StreamSetup ttStreamSetup;
|
| | | struct tt__Transport ttTransport;
|
| | | struct _trt__GetStreamUri req;
|
| | | struct _trt__GetStreamUriResponse rep;
|
| | |
|
| | | SOAP_ASSERT(NULL != MediaXAddr);
|
| | | SOAP_ASSERT(NULL != uri);
|
| | | |
| | | memset(uri, 0x00, sizeuri);
|
| | |
|
| | | SOAP_ASSERT(NULL != (soap = proto_soap_new(SOAP_SOCK_TIMEOUT)));
|
| | |
|
| | | memset(&req, 0x00, sizeof(req));
|
| | | memset(&rep, 0x00, sizeof(rep));
|
| | | memset(&ttStreamSetup, 0x00, sizeof(ttStreamSetup));
|
| | | memset(&ttTransport, 0x00, sizeof(ttTransport));
|
| | | |
| | | ttStreamSetup.Stream = tt__StreamType__RTP_Unicast;
|
| | | ttStreamSetup.Transport = &ttTransport;
|
| | | ttStreamSetup.Transport->Protocol = tt__TransportProtocol__RTSP;
|
| | | ttStreamSetup.Transport->Tunnel = NULL;
|
| | | req.StreamSetup = &ttStreamSetup;
|
| | | req.ProfileToken = ProfileToken;
|
| | |
|
| | | proto_SetAuthInfo(soap, username, passwd);
|
| | | result = soap_call___trt__GetStreamUri(soap, MediaXAddr, NULL, &req, &rep);
|
| | | SOAP_CHECK_ERROR(result, soap, "GetServices");
|
| | |
|
| | | dump_trt__GetStreamUriResponse(&rep);
|
| | |
|
| | | result = -1;
|
| | | if (NULL != rep.MediaUri) {
|
| | | if (NULL != rep.MediaUri->Uri) {
|
| | | if (sizeuri > strlen(rep.MediaUri->Uri)) {
|
| | | |
| | | strcpy(uri, rep.MediaUri->Uri);
|
| | | |
| | | result = 0;
|
| | | } else {
|
| | | SOAP_DBGERR("Not enough cache!\n");
|
| | | }
|
| | | }
|
| | | }
|
| | |
|
| | | EXIT:
|
| | |
|
| | | if (NULL != soap) {
|
| | | proto_soap_delete(soap);
|
| | | }
|
| | |
|
| | | return result;
|
| | |
|
| | | }
|
| | |
|
| | |
|
| New file |
| | |
| | | #ifndef __SRV_AV_DEMUX_H__ |
| | | #define __SRV_AV_DEMUX_H__ |
| | | |
| | | #include <semaphore.h> |
| | | #include <pthread.h> |
| | | |
| | | #include "capabilities/capa.h" |
| | | |
| | | #ifdef __cplusplus |
| | | extern "C" { |
| | | #endif |
| | | |
| | | #define VIDEO_PUT_DIR "/home/Work/Log_repo/video_log" |
| | | #define VIDEO_CONF_DATA "/usr/bin/video_conv.sh" |
| | | #define FFMPEG_BIN_DIR "/home/Work/Sources_temp/ffmpeg_sources/host/bin/ffmpeg" |
| | | |
| | | #define VIDEO_DURATION (5 * 60) //sec |
| | | |
| | | #define KB (1024.0) |
| | | #define MB (KB * 1024.0) |
| | | #define GB (MB * 1024.0) |
| | | #define DISK_FREE_THRES (0.05) |
| | | |
| | | /*the player work mode status*/ |
| | | enum wr_mode { |
| | | NORMAL, |
| | | PAUSE, |
| | | }; |
| | | |
| | | /*playback mode set key*/ |
| | | typedef struct _playback_key { |
| | | |
| | | /*format: 192.168.1.101*/ |
| | | char name[PTOTO_ADDRESS_ADD]; |
| | | |
| | | /*format: 2022-6-28*/ |
| | | char date[PTOTO_ADDRESS_ADD]; |
| | | |
| | | /*format: 21-32-19*/ |
| | | char time[PTOTO_ADDRESS_ADD]; |
| | | |
| | | } playback_key; |
| | | |
| | | /*the operational handle*/ |
| | | typedef struct _AVDevs { |
| | | |
| | | /*the devices capabilities*/ |
| | | struct tagCapabilities capa; |
| | | |
| | | /*the profies for each servies*/ |
| | | struct tagProfile *profiles; |
| | | |
| | | timer_t timer_id; |
| | | int timer_sec; |
| | | |
| | | sem_t sem_cap; |
| | | |
| | | volatile char run_stat; |
| | | volatile char slice_stat; |
| | | |
| | | char ip[PROTO_ADDRESS_SIZE]; |
| | | |
| | | char uri[PROTO_ADDRESS_SIZE + PTOTO_ADDRESS_ADD]; |
| | | char uri_data[PROTO_ADDRESS_SIZE + PTOTO_ADDRESS_ADD]; |
| | | |
| | | /*the device work stat*/ |
| | | char dev_stat; |
| | | |
| | | /*the process work stat*/ |
| | | char proc_stat; |
| | | |
| | | /*the stat record for pause work mode*/ |
| | | char pause_enable; |
| | | char pause_prev_loc[MAX_BUF_SIZE]; |
| | | char pause_cur_loc[MAX_BUF_SIZE]; |
| | | |
| | | enum wr_mode work_mode; |
| | | |
| | | } AVDevs; |
| | | |
| | | int proto_AVInit(void); |
| | | void proto_AVStart(AVDevs *DevData); |
| | | void proto_AVStop(AVDevs *DevData, enum wr_mode mode); |
| | | void proto_AVClose(void); |
| | | AVDevs *proto_AVGethandle(void); |
| | | void get_stream(AVDevs *DevData); |
| | | int playback_get_key(playback_key set, char *buf, int length); |
| | | |
| | | static int get_dir_with_key(char *dir_path, char *name, char *key, char *buf, int length); |
| | | static int get_file_with_key(char *dir_path, char *key, char *buf, int length, int flag); |
| | | static int get_dir_oldest(char *dir_path, char *buf, int length); |
| | | |
| | | static void cb_av_probe(char *DeviceXAddr); |
| | | static int video_file_create(char *buf, int len); |
| | | static int av_start_cap(AVDevs *DevData); |
| | | |
| | | static void system_date_get(char *buf, int len); |
| | | |
| | | #endif |
| | | |
| New file |
| | |
| | | #!/bin/sh |
| | | |
| | | exist_file() |
| | | { |
| | | if [ -e "$1" ] |
| | | then |
| | | return 1 |
| | | else |
| | | return 2 |
| | | fi |
| | | } |
| | | |
| | | if [ $# != 2 ] ; then |
| | | echo "USAGE: $0 media_src1 media_src2" |
| | | exit 1; |
| | | fi |
| | | |
| | | arg1=`basename $1` |
| | | |
| | | arg2=`basename $2` |
| | | |
| | | mainN1=${arg1%%.*} |
| | | mainE=${arg1#*.} |
| | | mainN2=${arg2%%.*} |
| | | |
| | | dirname=`dirname $1` |
| | | |
| | | exist_file $1 |
| | | value=$? |
| | | |
| | | if [ $value -eq 2 ] |
| | | then |
| | | echo "No source media ${arg1} found in the directory! Put it here firstly!\n" |
| | | exit |
| | | fi |
| | | |
| | | exist_file $2 |
| | | value=$? |
| | | |
| | | if [ $value -eq 2 ] |
| | | then |
| | | echo "No source media ${arg2} found in the directory! Put it here firstly!\n" |
| | | exit |
| | | fi |
| | | |
| | | output1=${mainN1}.ts |
| | | output2=${mainN2}.ts |
| | | |
| | | ffmpeg -i $1 -vcodec copy -acodec copy -vbsf h264_mp4toannexb ${output1} |
| | | ffmpeg -i $2 -vcodec copy -acodec copy -vbsf h264_mp4toannexb ${output2} |
| | | ffmpeg -i "concat:${output1}|${output2}" -acodec copy -vcodec copy -absf aac_adtstoasc ${mainN1}.${mainE} |
| | | |
| | | rm -rf ${output1} |
| | | rm -rf ${output2} |
| | | rm -rf $1 |
| | | mv ${mainN1}.${mainE} ${dirname} |
| | | |
| | | |
| | |
| | | return rep.__sizeProfiles;
|
| | | }
|
| | |
|
| | | int proto_GetVideoSource(const char *DeviceXAddr, char *buf, int len, const char *username, const char *passwd) {
|
| | | int result = 0;
|
| | | struct soap *soap = NULL;
|
| | | struct _trt__GetVideoSources *getVideoSources;
|
| | | struct _trt__GetVideoSourcesResponse *getVideoSourcesRes;
|
| | |
|
| | | SOAP_ASSERT(NULL != DeviceXAddr);
|
| | | SOAP_ASSERT(NULL != buf);
|
| | | SOAP_ASSERT(NULL != (soap = proto_soap_new(SOAP_SOCK_TIMEOUT)));
|
| | |
|
| | | getVideoSources = soap_new__trt__GetVideoSources(soap, 1);
|
| | | getVideoSourcesRes = soap_new__trt__GetVideoSourcesResponse(soap, 1);
|
| | |
|
| | | proto_SetAuthInfo(soap, username, passwd);
|
| | |
|
| | | result = soap_call___trt__GetVideoSources(soap, DeviceXAddr, NULL, getVideoSources, getVideoSourcesRes);
|
| | | SOAP_CHECK_ERROR(result, soap, "GetVideoSourc");
|
| | |
|
| | | if (getVideoSourcesRes->__sizeVideoSources <= 0) {
|
| | | |
| | | result = SOAP_NO_DATA;
|
| | | SOAP_CHECK_ERROR(result, soap, "GetVideoSourc");
|
| | |
|
| | | } else {
|
| | |
|
| | | for (int i = 0; i < getVideoSourcesRes->__sizeVideoSources; i++) {
|
| | |
|
| | | log_level_val(0, "get video source token: ", log_str, getVideoSourcesRes->VideoSources[i].token);
|
| | |
|
| | | if (i == 0) {
|
| | | strncpy(buf, getVideoSourcesRes->VideoSources[i].token, len);
|
| | | }
|
| | | }
|
| | | }
|
| | |
|
| | | EXIT:
|
| | | if (NULL != soap) {
|
| | | proto_soap_delete(soap);
|
| | | }
|
| | |
|
| | | return result;
|
| | | }
|
| | |
|
| | | int proto_GetCapabilities(const char *DeviceXAddr, struct tagCapabilities *capa, const char *username, const char *passwd)
|
| | | {
|
| | | int result = 0;
|
| | |
| | | #include <stdlib.h>
|
| | | #include <unistd.h>
|
| | | #include <semaphore.h>
|
| | | #include <string.h>
|
| | | #include <pthread.h>
|
| | | #include <signal.h>
|
| | | #include <errno.h>
|
| | |
| | | int ret;
|
| | |
|
| | | SOAP_ASSERT(DevData != NULL);
|
| | | SOAP_ASSERT(DevData->profilesToken != NULL);
|
| | | SOAP_ASSERT(DevData->profiles != NULL);
|
| | |
|
| | | ret = DevData->profilesToken->venc.Width;
|
| | | ret = DevData->profiles->venc.Width;
|
| | |
|
| | | return ret;
|
| | | }
|
| | |
| | | int ret;
|
| | |
|
| | | SOAP_ASSERT(DevData != NULL);
|
| | | SOAP_ASSERT(DevData->profilesToken != NULL);
|
| | | SOAP_ASSERT(DevData->profiles != NULL);
|
| | |
|
| | | ret = DevData->profilesToken->venc.Height;
|
| | | ret = DevData->profiles->venc.Height;
|
| | |
|
| | | return ret;
|
| | | }
|
| | |
|
| | | static void cb_probe(char *DeviceXAddr) {
|
| | |
|
| | | int len;
|
| | | char *pos_s, *pos_e;
|
| | |
|
| | | if (gPtzDevs == NULL) {
|
| | |
|
| | |
| | | SOAP_ASSERT(gPtzDevs != NULL);
|
| | |
|
| | | memset(gPtzDevs, 0x00, sizeof(PtzDevs));
|
| | |
|
| | | pos_s = strstr(DeviceXAddr, ADDR_PREFIX);
|
| | | pos_e = strstr(DeviceXAddr + strlen(ADDR_PREFIX), ADDR_LAST);
|
| | | len = pos_e - DeviceXAddr - strlen(ADDR_PREFIX);
|
| | | memcpy(gPtzDevs->ip, DeviceXAddr + strlen(ADDR_PREFIX), len);
|
| | | }
|
| | |
|
| | | proto_GetCapabilities(DeviceXAddr, &(gPtzDevs->capa), USERNAME, PASSWORD);
|
| | | proto_GetProfiles(gPtzDevs->capa.MediaXAddr, &(gPtzDevs->profilesToken), USERNAME, PASSWORD);
|
| | | proto_GetProfiles(gPtzDevs->capa.MediaXAddr, &(gPtzDevs->profiles), USERNAME, PASSWORD);
|
| | |
|
| | | }
|
| | |
|
| | |
| | | ret = sem_init(&(gPtzDevs->sem_tour), 0, 0);
|
| | | SOAP_ASSERT(ret == 0);
|
| | |
|
| | | timer_init(&(gPtzDevs->timer_id));
|
| | | timer_init(&(gPtzDevs->timer_id), ptz_timer_handler);
|
| | |
|
| | | gPtzDevs->dev_stat = DISABLE;
|
| | | pthread_mutex_init(&(gPtzDevs->node_mutex), NULL);
|
| | |
| | |
|
| | | timer_destroy(gPtzDevs->timer_id);
|
| | |
|
| | | free(gPtzDevs->profilesToken);
|
| | | free(gPtzDevs->profiles);
|
| | |
|
| | | free(gPtzDevs);
|
| | |
|
| | |
| | | }
|
| | |
|
| | | /*the timer process heandler*/
|
| | | static void timer_handler(union sigval para) {
|
| | | void ptz_timer_handler(union sigval para) {
|
| | |
|
| | | if (gPtzDevs != NULL) {
|
| | |
|
| | | pthread_mutex_lock(&(gPtzDevs->node_mutex));
|
| | |
|
| | | gPtzDevs->wt_stat = DISABLE;
|
| | |
|
| | | pthread_cond_signal(&(gPtzDevs->cond));
|
| | |
|
| | | pthread_mutex_unlock(&(gPtzDevs->node_mutex));
|
| | | }
|
| | |
|
| | | return;
|
| | | }
|
| | |
|
| | | static int timer_init(timer_t *timer_index) {
|
| | | struct sigevent event;
|
| | | timer_t timer;
|
| | | int ret;
|
| | |
|
| | | memset(&event, 0x00, sizeof(event));
|
| | | event.sigev_value.sival_int = ENABLE;
|
| | | event.sigev_value.sival_ptr = NULL;
|
| | | event.sigev_notify = SIGEV_THREAD;
|
| | | event.sigev_notify_function = timer_handler;
|
| | | |
| | | ret = timer_create(CLOCK_REALTIME, &event, &timer);
|
| | | if (ret) {
|
| | | return -1;
|
| | | }
|
| | |
|
| | | if (timer_index != NULL) {
|
| | | *timer_index = timer;
|
| | | }
|
| | |
|
| | | return 0;
|
| | | }
|
| | |
|
| | | static int timer_start(timer_t timer_index, int sec) {
|
| | | int ret;
|
| | | struct itimerspec ts;
|
| | |
|
| | | ts.it_interval.tv_sec = 0;
|
| | | ts.it_interval.tv_nsec = 0;
|
| | | ts.it_value.tv_sec = sec;
|
| | | ts.it_value.tv_nsec = 0;
|
| | | ret = timer_settime(timer_index, 0, &ts, NULL);
|
| | | if (ret) {
|
| | | return -1;
|
| | | }
|
| | |
|
| | | return ret;
|
| | | }
|
| | |
|
| | | static int timer_stop(timer_t timer_index) {
|
| | |
|
| | | int ret = timer_start(timer_index, 0);
|
| | |
|
| | | return ret;
|
| | | }
|
| | |
|
| | | static int timer_destroy(timer_t timer_index) {
|
| | | int ret;
|
| | |
|
| | | ret = timer_delete(timer_index);
|
| | | |
| | | return ret;
|
| | | }
|
| | |
|
| | | /*initialize the PTZ*/
|
| | |
| | | struct _tptz__GetStatusResponse *getStatusResponse = NULL;
|
| | |
|
| | | SOAP_ASSERT(DevData != NULL);
|
| | | SOAP_ASSERT(NULL != DevData->profilesToken);
|
| | | SOAP_ASSERT(NULL != DevData->profiles);
|
| | | SOAP_ASSERT(NULL != (soap = proto_soap_new(SOAP_SOCK_TIMEOUT)));
|
| | |
|
| | | getStatus = soap_new__tptz__GetStatus(soap, 1);
|
| | |
| | | strncpy(PTZXAddr, DevData->capa.PTZXAddr, PROTO_ADDRESS_SIZE);
|
| | | proto_SetAuthInfo(soap, username, passwd);
|
| | |
|
| | | getStatus->ProfileToken = DevData->profilesToken->token;
|
| | | getStatus->ProfileToken = DevData->profiles->token;
|
| | | result = soap_call___tptz__GetStatus(soap, PTZXAddr, NULL, getStatus, getStatusResponse);
|
| | | SOAP_CHECK_ERROR(result, soap, "proto_PTZ_GetStatus");
|
| | |
|
| | |
| | | char PTZXAddr[PROTO_ADDRESS_SIZE] = { 0x00 };
|
| | |
|
| | | SOAP_ASSERT(DevData != NULL);
|
| | | SOAP_ASSERT(NULL != DevData->profilesToken);
|
| | | SOAP_ASSERT(NULL != DevData->profiles);
|
| | | SOAP_ASSERT(NULL != (soap = proto_soap_new(SOAP_SOCK_TIMEOUT)));
|
| | |
|
| | | proto_PTZ_GetStatus(DevData, &pos_get, username, passwd);
|
| | |
| | |
|
| | | strncpy(PTZXAddr, DevData->capa.PTZXAddr, PROTO_ADDRESS_SIZE);
|
| | | proto_SetAuthInfo(soap, username, passwd);
|
| | | absMove->ProfileToken = DevData->profilesToken->token;
|
| | | absMove->ProfileToken = DevData->profiles->token;
|
| | |
|
| | | absMove->Position = soap_new_tt__PTZVector(soap, 1);
|
| | | absMove->Position->PanTilt = soap_new_tt__Vector2D(soap, 1);
|
| | |
| | | enum xsd__boolean xsd_false = xsd__boolean__false_;
|
| | |
|
| | | SOAP_ASSERT(DevData != NULL);
|
| | | SOAP_ASSERT(NULL != DevData->profilesToken);
|
| | | SOAP_ASSERT(NULL != DevData->profiles);
|
| | | SOAP_ASSERT(NULL != (soap = proto_soap_new(SOAP_SOCK_TIMEOUT)));
|
| | |
|
| | | struct _tptz__Stop *tptzStop = soap_new__tptz__Stop(soap, 1);
|
| | |
| | |
|
| | | strncpy(PTZXAddr, DevData->capa.PTZXAddr, PROTO_ADDRESS_SIZE);
|
| | | proto_SetAuthInfo(soap, username, passwd);
|
| | | tptzStop->ProfileToken = DevData->profilesToken->token;
|
| | | tptzStop->ProfileToken = DevData->profiles->token;
|
| | |
|
| | | tptzStop->PanTilt = &xsd_true;
|
| | | tptzStop->Zoom = &xsd_false;
|
| | |
| | | char PTZXAddr[PROTO_ADDRESS_SIZE] = { 0x00 };
|
| | |
|
| | | SOAP_ASSERT(DevData != NULL);
|
| | | SOAP_ASSERT(NULL != DevData->profilesToken);
|
| | | SOAP_ASSERT(NULL != DevData->profiles);
|
| | | SOAP_ASSERT(NULL != (soap = proto_soap_new(SOAP_SOCK_TIMEOUT)));
|
| | |
|
| | | struct _tptz__ContinuousMove* contMove = soap_new__tptz__ContinuousMove(soap, 1);
|
| | |
| | |
|
| | | strncpy(PTZXAddr, DevData->capa.PTZXAddr, PROTO_ADDRESS_SIZE);
|
| | | proto_SetAuthInfo(soap, username, passwd);
|
| | | contMove->ProfileToken = DevData->profilesToken->token;
|
| | | contMove->ProfileToken = DevData->profiles->token;
|
| | | contMove->Velocity = soap_new_tt__PTZSpeed(soap, 1);
|
| | | memset(contMove->Velocity, 0x00, sizeof(struct tt__PTZSpeed));
|
| | | contMove->Velocity->PanTilt = soap_new_tt__Vector2D(soap, 1);
|
| | |
| | | char PTZXAddr[PROTO_ADDRESS_SIZE] = { 0x00 };
|
| | |
|
| | | SOAP_ASSERT(DevData != NULL);
|
| | | SOAP_ASSERT(NULL != DevData->profilesToken);
|
| | | SOAP_ASSERT(NULL != DevData->profiles);
|
| | | SOAP_ASSERT(NULL != (soap = proto_soap_new(SOAP_SOCK_TIMEOUT)));
|
| | |
|
| | | pos_p = para_check(pos_p);
|
| | |
| | |
|
| | | strncpy(PTZXAddr, DevData->capa.PTZXAddr, PROTO_ADDRESS_SIZE);
|
| | | proto_SetAuthInfo(soap, username, passwd);
|
| | | relMove->ProfileToken = DevData->profilesToken->token;
|
| | | relMove->ProfileToken = DevData->profiles->token;
|
| | | relMove->Translation = (struct tt__PTZVector *)soap_malloc(soap, sizeof(struct tt__PTZVector));
|
| | | memset(relMove->Translation, 0x00, sizeof(struct tt__PTZVector));
|
| | | relMove->Translation->PanTilt = soap_new_tt__Vector2D(soap, 1);
|
| | |
| | | }
|
| | |
|
| | | /*set the focus-on functionality*/
|
| | | int proto_PTZ_ImagingSet(PtzDevs *DevData, float speed, const char *username, const char *passwd) {
|
| | | int proto_PTZ_ImagingSet(PtzDevs *DevData, enum PTZCMD cmd, float speed, const char *username, const char *passwd) {
|
| | | int result = 0;
|
| | | float speed_val;
|
| | | struct soap *soap = NULL;
|
| | |
| | | struct tt__ContinuousFocus *stContFocus = NULL;
|
| | | struct _timg__Move *stMoveReq = NULL;
|
| | | struct _timg__MoveResponse *stMoveRes = NULL;
|
| | | struct _timg__Stop *stStopReq = NULL;
|
| | | struct _timg__StopResponse *stStopRes = NULL;
|
| | |
|
| | | SOAP_ASSERT(NULL != DevData);
|
| | | SOAP_ASSERT(NULL != DevData->profilesToken);
|
| | | SOAP_ASSERT(NULL != DevData->profiles);
|
| | | SOAP_ASSERT(NULL != (soap = proto_soap_new(SOAP_SOCK_TIMEOUT)));
|
| | |
|
| | | stFocusMove = soap_new_tt__FocusMove(soap, 1);
|
| | | stContFocus = soap_new_tt__ContinuousFocus(soap, 1);
|
| | | |
| | | proto_SetAuthInfo(soap, username, passwd);
|
| | |
|
| | | |
| | | stMoveReq = soap_new__timg__Move(soap, 1);
|
| | | stMoveRes = soap_new__timg__MoveResponse(soap, 1);
|
| | |
|
| | | stStopReq = soap_new__timg__Stop(soap, 1);
|
| | | stStopRes = soap_new__timg__StopResponse(soap, 1);
|
| | |
|
| | | memset(stMoveReq, 0x00, sizeof(struct _timg__Move));
|
| | | memset(stMoveRes, 0x00, sizeof(struct _timg__MoveResponse));
|
| | |
|
| | | speed_val = pos_res_z(speed);
|
| | | memset(stStopReq, 0x00, sizeof(struct _timg__Stop));
|
| | | memset(stStopRes, 0x00, sizeof(struct _timg__StopResponse));
|
| | |
|
| | | stContFocus->Speed = speed_val;
|
| | | stMoveReq->Focus = stFocusMove;
|
| | | stMoveReq->Focus->Continuous = stContFocus;
|
| | |
|
| | | stMoveReq->VideoSourceToken = DevData->profiles->videoCfg.sourceToken;
|
| | | stStopReq->VideoSourceToken = DevData->profiles->videoCfg.sourceToken;
|
| | |
|
| | | proto_SetAuthInfo(soap, username, passwd);
|
| | |
|
| | | speed_val = pos_res_z(speed);
|
| | | switch(cmd) {
|
| | | case PTZ_CMD_FOCUS_IN:
|
| | | stContFocus->Speed = speed_val; |
| | | |
| | | break;
|
| | |
|
| | | case PTZ_CMD_FOCUS_OUT:
|
| | | stContFocus->Speed = speed_val * (-1);
|
| | | |
| | | break;
|
| | |
|
| | | default:
|
| | | result = soap_call___timg__Stop(soap, DevData->capa.MediaXAddr, NULL, stStopReq, stStopRes);
|
| | | SOAP_CHECK_ERROR(result, soap, "proto_PTZ_ImagingSet");
|
| | | |
| | | break;
|
| | | }
|
| | |
|
| | | stFocusMove->Continuous = stContFocus;
|
| | | stFocusMove->Absolute = NULL;
|
| | | stFocusMove->Relative = NULL;
|
| | |
|
| | | stMoveReq->Focus = stFocusMove;
|
| | | stMoveReq->VideoSourceToken = DevData->profilesToken->videoCfg.token;
|
| | |
|
| | | result = soap_call___timg__Move(soap, DevData->profilesToken->token, NULL, stMoveReq, stMoveRes);
|
| | | SOAP_CHECK_ERROR(result, soap, "proto_PTZ_FocusSet");
|
| | | result = soap_call___timg__Move(soap, DevData->capa.MediaXAddr, NULL, stMoveReq, stMoveRes);
|
| | | SOAP_CHECK_ERROR(result, soap, "proto_PTZ_ImagingSet");
|
| | |
|
| | | EXIT:
|
| | | if (NULL != soap) {
|
| | |
| | | char PTZXAddr[PROTO_ADDRESS_SIZE] = { 0x00 };
|
| | |
|
| | | SOAP_ASSERT(DevData != NULL);
|
| | | SOAP_ASSERT(NULL != DevData->profilesToken);
|
| | | SOAP_ASSERT(NULL != DevData->profiles);
|
| | | SOAP_ASSERT(NULL != (soap = proto_soap_new(SOAP_SOCK_TIMEOUT)));
|
| | |
|
| | | strncpy(PTZXAddr, DevData->capa.PTZXAddr, PROTO_ADDRESS_SIZE);
|
| | |
| | | memset(setPreset, 0x00, sizeof(struct _tptz__SetPreset));
|
| | | memset(setPresetRes, 0x00, sizeof(struct _tptz__SetPresetResponse));
|
| | |
|
| | | setPreset->ProfileToken = DevData->profilesToken->token;
|
| | | setPreset->ProfileToken = DevData->profiles->token;
|
| | | if (posName != NULL) {
|
| | | setPreset->PresetName = (char *)posName;
|
| | | }
|
| | |
| | | memset(getPresets, 0x00, sizeof(struct _tptz__GetPresets));
|
| | | memset(getPresetsRes, 0x00, sizeof(struct _tptz__GetPresetsResponse));
|
| | |
|
| | | getPresets->ProfileToken = DevData->profilesToken->token;
|
| | | getPresets->ProfileToken = DevData->profiles->token;
|
| | |
|
| | | result = soap_call___tptz__GetPresets(soap, PTZXAddr, NULL, getPresets, getPresetsRes);
|
| | | SOAP_CHECK_ERROR(result, soap, "proto_PTZPreset");
|
| | |
| | | memset(gotoPreset, 0x00, sizeof(struct _tptz__GotoPreset));
|
| | | memset(gotoPresetRes, 0x00, sizeof(struct _tptz__GotoPresetResponse));
|
| | |
|
| | | gotoPreset->ProfileToken = DevData->profilesToken->token;
|
| | | gotoPreset->ProfileToken = DevData->profiles->token;
|
| | |
|
| | | if (posToken != NULL) {
|
| | | sprintf(buf, "%d", *posToken);
|
| | |
| | | memset(rmPreset, 0x00, sizeof(struct _tptz__RemovePreset));
|
| | | memset(rmPresetRes, 0x00, sizeof(struct _tptz__RemovePresetResponse));
|
| | |
|
| | | rmPreset->ProfileToken = DevData->profilesToken->token;
|
| | | rmPreset->ProfileToken = DevData->profiles->token;
|
| | | if (posToken != NULL) {
|
| | | sprintf(buf, "%d", *posToken);
|
| | | rmPreset->PresetToken = buf;
|
| | |
| | | |
| | | #include "capabilities/capa.h" |
| | | |
| | | #define USERNAME "On_admin" |
| | | #define PASSWORD "a12345678" |
| | | |
| | | #define HK_IDS_2DE 1 |
| | | |
| | | #if defined(HK_IDS_2DE) |
| | |
| | | #define MIN_TOUR_TIME 15 |
| | | #define MIN_TOUR_POS 2 |
| | | |
| | | #define WT_TIME 5 |
| | | #define STOP_WT_TIME 3 |
| | | |
| | | #define MAX_IMG_SCALE 0.5 |
| | | |
| | | #define PI 3.14159 |
| | |
| | | #define COEF_FV_A 0.953 |
| | | #define COEF_FV_B 0.598 |
| | | #define COEF_FV_C 0.166 |
| | | |
| | | #define ENABLE 0 |
| | | #define DISABLE 1 |
| | | |
| | | /*PTZ working stat*/ |
| | | enum PTZStat { |
| | |
| | | PTZ_CMD_RIGHTDOWN, |
| | | PTZ_CMD_ZOOM_IN, |
| | | PTZ_CMD_ZOOM_OUT, |
| | | PTZ_CMD_FOCUS_IN, |
| | | PTZ_CMD_FOCUS_OUT, |
| | | PTZ_CMD_FOCUS_STOP, |
| | | }; |
| | | |
| | | /*the tradditional preset control command*/ |
| | |
| | | |
| | | struct tagCapabilities capa; |
| | | |
| | | struct tagProfile *profilesToken; |
| | | struct tagProfile *profiles; |
| | | |
| | | PresetToure_node *posNode; |
| | | int posNode_count; |
| | |
| | | |
| | | /*the touring process work stat*/ |
| | | char proc_stat; |
| | | |
| | | char ip[PROTO_ADDRESS_SIZE]; |
| | | |
| | | enum tourType tour_type; |
| | | |
| | |
| | | |
| | | int proto_PTZPreset(PtzDevs *DevData, const char *posName, enum PreSetCMD cmd, \ |
| | | int *posToken, const char *username, const char *passwd); |
| | | int proto_PTZ_ImagingSet(PtzDevs *DevData, float speed, const char *username, const char *passwd); |
| | | int proto_PTZ_ImagingSet(PtzDevs *DevData, enum PTZCMD cmd, float speed, const char *username, const char *passwd); |
| | | |
| | | static void *task_preset_touring(void *arg); |
| | | float proto_PTZZoom_get(PtzDevs *DevData, int x0, int y0, int x1, int y1); |
| | |
| | | void proto_PTZWaitStopped(PtzDevs *DevData, const char *username, const char *passwd); |
| | | void proto_PTZPreset_tour_stop(PtzDevs *DevData); |
| | | |
| | | static void timer_handler(union sigval para); |
| | | static int timer_init(timer_t *timer_index); |
| | | static int timer_start(timer_t timer_index, int sec); |
| | | static int timer_stop(timer_t timer_index); |
| | | static int timer_destroy(timer_t timer_index); |
| | | static void ptz_timer_handler(union sigval para); |
| | | |
| | | #ifdef __cplusplus |
| | | } |
| | |
| | | OBJECTS_ONVIF := $(patsubst %.c,$(TEMPDIR)%.o,$(filter %.c, $(SOURCES_CORE)))
|
| | | OBJECTS_COMM := $(patsubst %.c,$(TEMPDIR)%.o,$(filter %.c, $(SOURCES_COMM)))
|
| | |
|
| | | FFMPEG_DIR = ../../thirdparty/ffmpeg
|
| | | OPENSSL_DIR = ../../thirdparty/openssl
|
| | |
|
| | | #
|
| | | INCLUDE += -I../../core/ \
|
| | | -I../../comm/ \
|
| | | -I$(FFMPEG_DIR)/include \
|
| | | -I$(OPENSSL_DIR)/include
|
| | | CFLAGS += $(INCLUDE)
|
| | |
|
| | | LDFLAGS += -L$(FFMPEG_DIR)/lib
|
| | | LDFLAGS += -L$(OPENSSL_DIR)/lib
|
| | | LDLIBS += -lavcodec -lavdevice -lavfilter -lavformat \
|
| | | -lavutil -lswresample -lswscale
|
| | | LDLIBS += -lcrypto -lssl -lpthread -ldl
|
| | |
|
| | | %.o: %.cpp
|
| New file |
| | |
| | | CC := gcc
|
| | | CPP := g++ |
| | | LD := ld
|
| | | AR := ar
|
| | | STRIP := strip
|
| | | RM := rm
|
| | |
|
| | | PROGRAM = av_stream_test
|
| | |
|
| | | SOURCES += av_test.c
|
| | |
|
| | | CFLAGS += -Wall -DWITH_DOM -DWITH_NONAMESPACES -DWITH_OPENSSL -Wno-unused
|
| | |
|
| | | OBJECTS := $(patsubst %.c,$(TEMPDIR)%.o,$(filter %.c, $(SOURCES)))
|
| | |
|
| | | %.o: %.cpp
|
| | | @echo " CPP " $@; |
| | | @$(CPP) $(CFLAGS) -c -o $@ $<
|
| | |
|
| | | %.o: %.c |
| | | @echo " CC " $@; |
| | | @$(CC) $(CFLAGS) -c -o $@ $<
|
| | |
|
| | | FFMPEG_DIR = ../../thirdparty/ffmpeg
|
| | | OPENSSL_DIR = ../../thirdparty/openss
|
| | |
|
| | | LDFLAGS += -L$(FFMPEG_DIR)/lib
|
| | | LDFLAGS += -L$(OPENSSL_DIR)/lib
|
| | | LDFLAGS += -L../../
|
| | | LDLIBS += -lonvif_std
|
| | | LDLIBS += -lavcodec -lavdevice -lavfilter -lavformat \
|
| | | -lavutil -lswresample -lswscale
|
| | | LDLIBS += -lcrypto -lssl -lpthread -ldl -lrt
|
| | | LDLIBS += -lprotobuf -lprotobuf-lite
|
| | |
|
| | | INCLUDE += -I../../core/ \
|
| | | -I../../comm/ \
|
| | | -I../../service \
|
| | | -I$(FFMPEG_DIR)/include \
|
| | | -I$(OPENSSL_DIR)/include
|
| | | CFLAGS += $(INCLUDE)
|
| | |
|
| | | all: $(OBJECTS)
|
| | | $(CC) -o $(PROGRAM) $(OBJECTS) $(LDFLAGS) $(LDLIBS) $(CFLAGS)
|
| | |
|
| | | clean:
|
| | | $(RM) -f $(OBJECTS)
|
| | | $(RM) -f $(PROGRAM)
|
| | |
|
| | | allclean: clean
|
| | | $(RM) -f $(OBJECTS_ONVIF)
|
| | |
|
| New file |
| | |
| | | #include <stdio.h>
|
| | | #include <stdlib.h>
|
| | | #include <assert.h>
|
| | |
|
| | | #include "PTZBinding.nsmap"
|
| | | #include "av_demux/av_demux.h"
|
| | |
|
| | | int main(int argc, char **argv)
|
| | | {
|
| | | int ret;
|
| | | char parse_buf[MAX_BUF_SIZE] = { 0x00 };
|
| | | playback_key data_set = {"192.168.1.101", "2022-7-3", "21-52-16"};
|
| | | AVDevs *handle = NULL;
|
| | |
|
| | | ret = proto_AVInit();
|
| | | if (ret < 0) {
|
| | | printf("AV stream initialization failure!\n");
|
| | |
|
| | | return 0;
|
| | | }
|
| | |
|
| | | printf("start the av stream:\n");
|
| | | handle = proto_AVGethandle();
|
| | | proto_AVStart(handle);
|
| | | |
| | | sleep(5 * 60 * 2);
|
| | |
|
| | | printf("stop the av stream now:\n");
|
| | | proto_AVStop(handle, NORMAL);
|
| | |
|
| | | sleep(3);
|
| | |
|
| | | printf("re-start the AV now:\n");
|
| | | proto_AVStart(handle);
|
| | |
|
| | | sleep(120);
|
| | |
|
| | | printf("pause the av stream now:\n");
|
| | | proto_AVStop(handle, PAUSE);
|
| | |
|
| | | sleep(20);
|
| | |
|
| | | printf("resume the av:\n");
|
| | | proto_AVStart(handle);
|
| | |
|
| | | sleep(200);
|
| | |
|
| | | printf("stop the av");
|
| | | proto_AVStop(handle, NORMAL);
|
| | |
|
| | | sleep(3);
|
| | | |
| | | ret = playback_get_key(data_set, parse_buf, sizeof(parse_buf));
|
| | | if (ret > 0) {
|
| | | printf("found the playback file: %s\n", parse_buf);
|
| | | } else {
|
| | | printf("the playback file is not existed!\n");
|
| | | }
|
| | |
|
| | | sleep(3000);
|
| | | printf("now exit the process:\n");
|
| | | proto_AVClose();
|
| | |
|
| | | return 0;
|
| | | }
|
| | |
|
| | |
| | | @echo " CC " $@;
|
| | | @$(CC) $(CFLAGS) -c -o $@ $<
|
| | |
|
| | | FFMPEG_DIR = ../../thirdparty/ffmpeg
|
| | | OPENSSL_DIR = ../../thirdparty/openss
|
| | |
|
| | | LDFLAGS += -L$(FFMPEG_DIR)/lib
|
| | | LDFLAGS += -L$(OPENSSL_DIR)/lib
|
| | | LDFLAGS += -L../../
|
| | | LDLIBS += -lonvif_std
|
| | | LDLIBS += -lavcodec -lavdevice -lavfilter -lavformat \
|
| | | -lavutil -lswresample -lswscale
|
| | | LDLIBS += -lcrypto -lssl -lpthread -ldl -lm -lrt
|
| | |
|
| | | INCLUDE += -I../../core/ \
|
| | | -I../../comm/ \
|
| | | -I../../service \
|
| | | -I$(FFMPEG_DIR)/include \
|
| | | -I$(OPENSSL_DIR)/include
|
| | | CFLAGS += $(INCLUDE)
|
| | |
|
| | |
| | | @echo " CC " $@;
|
| | | @$(CC) $(CFLAGS) -c -o $@ $<
|
| | |
|
| | | FFMPEG_DIR = ../../thirdparty/ffmpeg
|
| | | OPENSSL_DIR = ../../thirdparty/openss
|
| | |
|
| | | LDFLAGS += -L$(FFMPEG_DIR)/lib
|
| | | LDFLAGS += -L$(OPENSSL_DIR)/lib
|
| | | LDFLAGS += -L../../
|
| | | LDLIBS += -lonvif_std
|
| | | LDLIBS += -lavcodec -lavdevice -lavfilter -lavformat \
|
| | | -lavutil -lswresample -lswscale
|
| | | LDLIBS += -lcrypto -lssl -lpthread -ldl -lm -lrt
|
| | |
|
| | | INCLUDE += -I../../core/ \
|
| | | -I../../comm/ \
|
| | | -I../../service \
|
| | | -I$(FFMPEG_DIR)/include \
|
| | | -I$(OPENSSL_DIR)/include
|
| | | CFLAGS += $(INCLUDE)
|
| | |
|
| | |
| | | {
|
| | | int ret;
|
| | | PosCur pos_get;
|
| | | float data;
|
| | | int preset0, preset1, preset2;
|
| | | float pval, tval, zval;
|
| | | float speed_p, speed_t, speed_z;
|
| | |
| | | * secondly, zoom in the object that is describled with left-up and right-down pixel;
|
| | | * finally, restore the image as original size;
|
| | | */
|
| | | float data;
|
| | | proto_PTZ_GetStatus(handle, &pos_get, USERNAME, PASSWORD);
|
| | | proto_PTZGetPT(handle, 0, 0, &pval, &tval, USERNAME, PASSWORD);
|
| | | proto_PTZSet(handle, pval, tval, pos_get.z, USERNAME, PASSWORD);
|