Unverified Commit 388c70f0 authored by Stefan Profanter's avatar Stefan Profanter Committed by GitHub
Browse files

Merge 1.0 into master (#3067)

Merge 1.0 into master
parents 1666968d a0c78752
No related merge requests found
Showing with 314 additions and 347 deletions
+314 -347
Dockerfile
/build/*
......@@ -6,6 +6,9 @@ env:
# GITAUTH:
- secure: nSunY54Wp5HkQCHHbKwlwpbaKyqRVIu/0EnhaoJSwhM1wqerQV/E5d/2JelO9/tZgbungAO7wk/fjutRMVc7d378RTIPwS8vHpvZfEoGhCFsLoTOlqESzsZFBup2H5t1lpQ23jRHDOxlLdJy2lz5U+zd1YnYgDXqdDFjegsIYdo=
- PYTHON=python2
# For tag builds we do not have the base branch in TRAVIS_BRANCH, therefore store it in BRANCH_FOR_TAG
- BRANCH_FOR_TAG=$(git ls-remote origin | sed -n "\|$TRAVIS_COMMIT\s\+refs/heads/|{s///p}")
dist: trusty
......
......@@ -456,7 +456,7 @@ if(NOT UA_COMPILE_AS_CXX AND (CMAKE_COMPILER_IS_GNUCC OR "x${CMAKE_C_COMPILER_ID
set(CMAKE_SHARED_LIBRARY_LINK_C_FLAGS "") # cmake sets -rdynamic by default
# Debug
if(BUILD_TYPE_LOWER_CASE STREQUAL "debug")
if(BUILD_TYPE_LOWER_CASE STREQUAL "debug" AND UNIX)
if("x${CMAKE_C_COMPILER_ID}" STREQUAL "xClang" AND NOT UA_ENABLE_UNIT_TESTS_MEMCHECK)
# Add default sanitizer settings when using clang and Debug build.
# This allows e.g. CLion to find memory locations for SegFaults
......@@ -467,7 +467,7 @@ if(NOT UA_COMPILE_AS_CXX AND (CMAKE_COMPILER_IS_GNUCC OR "x${CMAKE_C_COMPILER_ID
endif()
endif()
if(UA_ENABLE_HARDENING AND (CMAKE_BUILD_TYPE STREQUAL "Release") OR (CMAKE_BUILD_TYPE STREQUAL "RelWithDebInfo"))
if(UA_ENABLE_HARDENING AND ((CMAKE_BUILD_TYPE STREQUAL "Release") OR (CMAKE_BUILD_TYPE STREQUAL "RelWithDebInfo")))
check_cc_flag("-D_FORTIFY_SOURCE=2") # run-time buffer overflow detection (needs at least -O1)
endif()
......
FROM alpine:3.5
RUN apk add --no-cache cmake gcc g++ musl-dev python py-pip make && rm -rf /var/cache/apk/*
ADD . /tmp/open62541
WORKDIR /tmp/open62541/build
RUN cmake -DUA_ENABLE_AMALGAMATION=true \
-DBUILD_SHARED_LIBS=true \
/tmp/open62541
FROM alpine:3.10
RUN apk add --no-cache cmake gcc git g++ musl-dev mbedtls-dev python py-pip make && rm -rf /var/cache/apk/*
ADD . /opt/open62541
# Get all the git tags to make sure we detect the correct version with git describe
WORKDIR /opt/open62541
RUN git remote add github-upstream https://github.com/open62541/open62541.git
RUN git fetch --tags github-upstream
WORKDIR /opt/open62541/build
RUN cmake -DBUILD_SHARED_LIBS=ON \
-DCMAKE_BUILD_TYPE=Debug \
-DUA_BUILD_EXAMPLES=ON \
# Hardening needs to be disabled, otherwise the docker build takes too long and travis fails
-DUA_ENABLE_HARDENING=OFF \
-DUA_ENABLE_ENCRYPTION=ON \
-DUA_ENABLE_SUBSCRIPTIONS=ON \
-DUA_ENABLE_SUBSCRIPTIONS_EVENTS=ON \
-DUA_NAMESPACE_ZERO=FULL \
/opt/open62541
RUN make -j
RUN cp *.h /usr/include/ && \
cp bin/*.so /usr/lib
RUN make install
WORKDIR /opt/open62541
# Generate certificates
RUN apk add --no-cache python-dev linux-headers openssl && rm -rf /var/cache/apk/*
RUN pip install netifaces==0.10.9
RUN mkdir -p /opt/open62541/pki/created
RUN python /opt/open62541/tools/certs/create_self-signed.py /opt/open62541/pki/created
EXPOSE 4840
CMD ["/opt/open62541/build/bin/examples/server_ctt" , "/opt/open62541/pki/created/server_cert.der", "/opt/open62541/pki/created/server_key.der", "--enableUnencrypted", "--enableAnonymous"]
......@@ -11,7 +11,9 @@ The library is [available](https://github.com/open62541/open62541/releases) in s
Build Status:
[![Build Status](https://img.shields.io/travis/open62541/open62541/master.svg)](https://travis-ci.org/open62541/open62541)
[![Build Status](https://dev.azure.com/open62541/open62541/_apis/build/status/open62541.open62541?branchName=master)](https://dev.azure.com/open62541/open62541/_build/latest?definitionId=1&branchName=master)
[![Build Status](https://ci.appveyor.com/api/projects/status/github/open62541/open62541?branch=master&svg=true)](https://ci.appveyor.com/project/open62541/open62541/branch/master)
[![Build Status](https://img.shields.io/docker/cloud/build/open62541/open62541)](https://cloud.docker.com/u/open62541/repository/docker/open62541/open62541)
Code Quality:
......@@ -125,11 +127,39 @@ A list of projects and companies using our open62541 stack can be found in our W
https://github.com/open62541/open62541/wiki/References-to-open62541
## Installation and code usage
For every release, we provide some pre-packed release packages which you can directly use in your compile infrastructure.
Have a look at the [release page](https://github.com/open62541/open62541/releases) and the corresponding attached assets.
A more detailed explanation on how to install the open62541 SDK is given in our [documentation](https://open62541.org/doc/current/installing.html).
You can not directly download a .zip package from the main branches using the Github UI, since then some of the submodules and version strings are missing.
Therefore you have three options to install and use this stack:
- **Recommended:** Use any of the prepared packages attached to every release or in the package repository of your distro (if available).
Please check the install guide for more info.
- Download a .zip package of special `pack/` branches.
These pack branches are up-to-date with the corresponding base branches, but already have the submodules in-place and the version string set correctly.
Here are some direct download links for the current pack branches:
- [pack/master.zip](https://github.com/open62541/open62541/archive/pack/master.zip)
- [pack/1.0.zip](https://github.com/open62541/open62541/archive/pack/1.0.zip)
- Clone this repository and initialize all the submodules using `git submodule update --init --recursive`. Then either use `make install` or setup your CMake project correspondingly.
## Examples
A complete list of examples can be found in the [examples directory](https://github.com/open62541/open62541/tree/master/examples).
To build the examples, we recommend to install the open62541 project as mentioned in previous section.
### Example Server Implementation
Compile the examples with the single-file distribution `open62541.h/.c` header and source file.
Using the GCC compiler, just run ```gcc -std=c99 -DUA_ARCHITECTURE_POSIX <server.c> open62541.c -o server``` (under Windows you may need to add ``` -lws2_32```
The following simple server example can be built using gcc, after you installed open62541 on your system.
Using the GCC compiler, just run ```gcc -std=c99 -lopen62541 -DUA_ARCHITECTURE_POSIX <server.c> -o server``` (under Windows you may need to add ``` -lws2_32```
and change `-DUA_ARCHITECTURE_POSIX` to `-DUA_ARCHITECTURE_WIN32`).
```c
#include <signal.h>
......
......@@ -367,7 +367,6 @@ ServerNetworkLayerTCP_start(UA_ServerNetworkLayer *nl, const UA_String *customHo
/* Get the discovery url from the hostname */
UA_String du = UA_STRING_NULL;
char discoveryUrlBuffer[256];
char hostnameBuffer[256];
if (customHostname->length) {
du.length = (size_t)UA_snprintf(discoveryUrlBuffer, 255, "opc.tcp://%.*s:%d/",
(int)customHostname->length,
......@@ -375,12 +374,14 @@ ServerNetworkLayerTCP_start(UA_ServerNetworkLayer *nl, const UA_String *customHo
layer->port);
du.data = (UA_Byte*)discoveryUrlBuffer;
}else{
char hostnameBuffer[256];
if(UA_gethostname(hostnameBuffer, 255) == 0) {
du.length = (size_t)UA_snprintf(discoveryUrlBuffer, 255, "opc.tcp://%s:%d/",
hostnameBuffer, layer->port);
du.data = (UA_Byte*)discoveryUrlBuffer;
} else {
UA_LOG_ERROR(layer->logger, UA_LOGCATEGORY_NETWORK, "Could not get the hostname");
return UA_STATUSCODE_BADINTERNALERROR;
}
}
UA_String_copy(&du, &nl->discoveryUrl);
......
......@@ -57,7 +57,8 @@ jobs:
displayName: Install Requirements
- powershell: ./tools/azure-devops/build.ps1
displayName: "Build: $(CC_NAME)"
errorActionPreference: continue # Nodeset Compiler prints to stderror
errorActionPreference: continue # If set to Stop, we only get a truncated exception message. Error is handled by checking exit code
- task: PublishBuildArtifacts@1
inputs:
......@@ -87,7 +88,7 @@ jobs:
displayName: Install Requirements
- powershell: ./tools/azure-devops/build.ps1
displayName: "Build: $(CC_NAME)"
errorActionPreference: continue # Nodeset Compiler prints to stderror
errorActionPreference: continue # If set to Stop, we only get a truncated exception message. Error is handled by checking exit code
- task: PublishBuildArtifacts@1
inputs:
......
......@@ -16,7 +16,7 @@ Package: libopen62541-<soname>-dev
Section: libdevel
Architecture: any
Multi-Arch: same
Depends: libopen62541-<soname> (= ${binary:Version}), ${misc:Depends}
Depends: libopen62541-<soname> (= ${binary:Version}), ${misc:Depends}, python
Description: Development header files for open62541
open62541 is an open source C (C99) implementation of the OPC UA standard
......
/*
https://github.com/superwills/NibbleAndAHalf
base64.h -- Fast base64 encoding and decoding.
version 1.0.0, April 17, 2013 143a
Copyright (C) 2013 William Sherif
This software is provided 'as-is', without any express or implied
warranty. In no event will the authors be held liable for any damages
arising from the use of this software.
Permission is granted to anyone to use this software for any purpose,
including commercial applications, and to alter it and redistribute it
freely, subject to the following restrictions:
1. The origin of this software must not be misrepresented; you must not
claim that you wrote the original software. If you use this software
in a product, an acknowledgment in the product documentation would be
appreciated but is not required.
2. Altered source versions must be plainly marked as such, and must not be
misrepresented as being the original software.
3. This notice may not be removed or altered from any source distribution.
William Sherif
will.sherif@gmail.com
YWxsIHlvdXIgYmFzZSBhcmUgYmVsb25nIHRvIHVz
*/
* Base64 encoding: Copyright (c) 2005-2011, Jouni Malinen <j@w1.fi>
* This software may be distributed under the terms of the BSD license.
*
* Base64 decoding: Copyright (c) 2016, polfosol
* Posted at https://stackoverflow.com/a/37109258 under the CC-BY-SA Creative
* Commons license.
*/
#include "base64.h"
#include <open62541/types.h>
#include <stdio.h>
#include <stdlib.h>
static const char* b64="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/" ;
// maps A=>0,B=>1..
static const unsigned char unb64[]={
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, //10
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, //20
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, //30
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, //40
0, 0, 0, 62, 0, 0, 0, 63, 52, 53, //50
54, 55, 56, 57, 58, 59, 60, 61, 0, 0, //60
0, 0, 0, 0, 0, 0, 1, 2, 3, 4, //70
5, 6, 7, 8, 9, 10, 11, 12, 13, 14, //80
15, 16, 17, 18, 19, 20, 21, 22, 23, 24, //90
25, 0, 0, 0, 0, 0, 0, 26, 27, 28, //100
29, 30, 31, 32, 33, 34, 35, 36, 37, 38, //110
39, 40, 41, 42, 43, 44, 45, 46, 47, 48, //120
49, 50, 51, 0, 0, 0, 0, 0, 0, 0, //130
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, //140
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, //150
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, //160
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, //170
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, //180
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, //190
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, //200
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, //210
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, //220
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, //230
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, //240
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, //250
0, 0, 0, 0, 0, 0,
}; // This array has 256 elements
// Converts binary data of length=len to base64 characters.
// Length of the resultant string is stored in flen
// (you must pass pointer flen).
char* UA_base64( const void* binaryData, int len, int *flen )
{
const unsigned char* bin = (const unsigned char*) binaryData ;
char* res ;
int rc = 0 ; // result counter
int byteNo ; // I need this after the loop
int modulusLen = len % 3 ;
int pad = ((modulusLen&1)<<1) + ((modulusLen&2)>>1) ; // 2 gives 1 and 1 gives 2, but 0 gives 0.
static const unsigned char base64_table[65] =
"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
*flen = 4*(len + pad)/3 ;
res = (char*) malloc( (size_t)(*flen + 1) ) ; // and one for the null
if( !res )
{
puts( "ERROR: base64 could not allocate enough memory." ) ;
puts( "I must stop because I could not get enough" ) ;
return 0;
unsigned char *
UA_base64(const unsigned char *src, size_t len, size_t *out_len) {
if(len == 0) {
*out_len = 0;
return (unsigned char*)UA_EMPTY_ARRAY_SENTINEL;
}
for( byteNo = 0 ; byteNo <= len-3 ; byteNo+=3 )
{
unsigned char BYTE0=bin[byteNo];
unsigned char BYTE1=bin[byteNo+1];
unsigned char BYTE2=bin[byteNo+2];
res[rc++] = b64[ BYTE0 >> 2 ] ;
res[rc++] = b64[ ((0x3&BYTE0)<<4) + (BYTE1 >> 4) ] ;
res[rc++] = b64[ ((0x0f&BYTE1)<<2) + (BYTE2>>6) ] ;
res[rc++] = b64[ 0x3f&BYTE2 ] ;
}
if( pad==2 )
{
res[rc++] = b64[ bin[byteNo] >> 2 ] ;
res[rc++] = b64[ (0x3&bin[byteNo])<<4 ] ;
res[rc++] = '=';
res[rc++] = '=';
}
else if( pad==1 )
{
res[rc++] = b64[ bin[byteNo] >> 2 ] ;
res[rc++] = b64[ ((0x3&bin[byteNo])<<4) + (bin[byteNo+1] >> 4) ] ;
res[rc++] = b64[ (0x0f&bin[byteNo+1])<<2 ] ;
res[rc++] = '=';
}
res[rc]=0; // NULL TERMINATOR! ;)
return res ;
size_t olen = 4*((len + 2) / 3); /* 3-byte blocks to 4-byte */
if(olen < len)
return NULL; /* integer overflow */
unsigned char *out = (unsigned char*)UA_malloc(olen);
if(!out)
return NULL;
const unsigned char *end = src + len;
const unsigned char *in = src;
unsigned char *pos = out;
while(end - in >= 3) {
*pos++ = base64_table[in[0] >> 2];
*pos++ = base64_table[((in[0] & 0x03) << 4) | (in[1] >> 4)];
*pos++ = base64_table[((in[1] & 0x0f) << 2) | (in[2] >> 6)];
*pos++ = base64_table[in[2] & 0x3f];
in += 3;
}
if(end - in) {
*pos++ = base64_table[in[0] >> 2];
if(end - in == 1) {
*pos++ = base64_table[(in[0] & 0x03) << 4];
*pos++ = '=';
} else {
*pos++ = base64_table[((in[0] & 0x03) << 4) | (in[1] >> 4)];
*pos++ = base64_table[(in[1] & 0x0f) << 2];
}
*pos++ = '=';
}
*out_len = (size_t)(pos - out);
return out;
}
unsigned char* UA_unbase64( const char* ascii, int len, int *flen )
{
const unsigned char *safeAsciiPtr = (const unsigned char*)ascii ;
unsigned char *bin ;
int cb=0;
int charNo;
int pad = 0 ;
if( len < 2 ) { // 2 accesses below would be OOB.
// catch empty string, return NULL as result.
puts( "ERROR: You passed an invalid base64 string (too short). You get NULL back." ) ;
*flen=0;
return 0 ;
static const uint32_t from_b64[256] = {
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 62, 63, 62, 62, 63,
52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 0, 0, 0, 0, 0, 0,
0, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14,
15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 0, 0, 0, 0, 63,
0, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40,
41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51};
unsigned char *
UA_unbase64(const unsigned char *src, size_t len, size_t *out_len) {
if(len == 0) {
*out_len = 0;
return (unsigned char*)UA_EMPTY_ARRAY_SENTINEL;
}
if( safeAsciiPtr[ len-1 ]=='=' ) ++pad ;
if( safeAsciiPtr[ len-2 ]=='=' ) ++pad ;
*flen = 3*len/4 - pad ;
bin = (unsigned char*)malloc( (size_t) (*flen) ) ;
if( !bin )
{
puts( "ERROR: unbase64 could not allocate enough memory." ) ;
puts( "I must stop because I could not get enough" ) ;
return 0;
const unsigned char *p = src;
size_t pad1 = len % 4 || p[len - 1] == '=';
size_t pad2 = pad1 && (len % 4 > 2 || p[len - 2] != '=');
const size_t last = (len - pad1) / 4 << 2;
unsigned char *str = (unsigned char*)UA_malloc(last / 4 * 3 + pad1 + pad2);
if(!str)
return NULL;
unsigned char *pos = str;
for(size_t i = 0; i < last; i += 4) {
uint32_t n = from_b64[p[i]] << 18 | from_b64[p[i + 1]] << 12 |
from_b64[p[i + 2]] << 6 | from_b64[p[i + 3]];
*pos++ = (unsigned char)(n >> 16);
*pos++ = (unsigned char)(n >> 8 & 0xFF);
*pos++ = (unsigned char)(n & 0xFF);
}
for( charNo=0; charNo <= len - 4 - pad ; charNo+=4 )
{
int A=unb64[safeAsciiPtr[charNo]];
int B=unb64[safeAsciiPtr[charNo+1]];
int C=unb64[safeAsciiPtr[charNo+2]];
int D=unb64[safeAsciiPtr[charNo+3]];
bin[cb++] = (unsigned char)((A<<2) | (B>>4)) ;
bin[cb++] = (unsigned char)((B<<4) | (C>>2)) ;
bin[cb++] = (unsigned char)((C<<6) | (D)) ;
if(pad1) {
uint32_t n = from_b64[p[last]] << 18 | from_b64[p[last + 1]] << 12;
*pos++ = (unsigned char)(n >> 16);
if(pad2) {
n |= from_b64[p[last + 2]] << 6;
*pos++ = (unsigned char)(n >> 8 & 0xFF);
}
}
if( pad==1 )
{
int A=unb64[safeAsciiPtr[charNo]];
int B=unb64[safeAsciiPtr[charNo+1]];
int C=unb64[safeAsciiPtr[charNo+2]];
bin[cb++] = (unsigned char)((A<<2) | (B>>4)) ;
bin[cb++] = (unsigned char)((B<<4) | (C>>2)) ;
}
else if( pad==2 )
{
int A=unb64[safeAsciiPtr[charNo]];
int B=unb64[safeAsciiPtr[charNo+1]];
bin[cb++] = (unsigned char)((A<<2) | (B>>4)) ;
}
return bin ;
*out_len = (uintptr_t)(pos - str);
return str;
}
/*
https://github.com/superwills/NibbleAndAHalf
base64.h -- Fast base64 encoding and decoding.
version 1.0.0, April 17, 2013 143a
Copyright (C) 2013 William Sherif
This software is provided 'as-is', without any express or implied
warranty. In no event will the authors be held liable for any damages
arising from the use of this software.
Permission is granted to anyone to use this software for any purpose,
including commercial applications, and to alter it and redistribute it
freely, subject to the following restrictions:
1. The origin of this software must not be misrepresented; you must not
claim that you wrote the original software. If you use this software
in a product, an acknowledgment in the product documentation would be
appreciated but is not required.
2. Altered source versions must be plainly marked as such, and must not be
misrepresented as being the original software.
3. This notice may not be removed or altered from any source distribution.
William Sherif
will.sherif@gmail.com
YWxsIHlvdXIgYmFzZSBhcmUgYmVsb25nIHRvIHVz
*/
#ifndef UA_BASE64_H_
#define UA_BASE64_H_
#ifdef __cplusplus
extern "C" {
#endif
char* UA_base64( const void* binaryData, int len, int *flen );
unsigned char* UA_unbase64( const char* ascii, int len, int *flen );
#ifdef __cplusplus
}
#endif
#include <open62541/config.h>
_UA_BEGIN_DECLS
#include <stddef.h>
/**
* base64_encode - Base64 encode
* @src: Data to be encoded
* @len: Length of the data to be encoded
* @out_len: Pointer to output length variable
* Returns: Allocated buffer of out_len bytes of encoded data,
* or %NULL on failure. The output is NOT Null-terminated. */
unsigned char *
UA_base64(const unsigned char *src, size_t len, size_t *out_len);
/**
* base64_decode - Base64 decode
* @src: Data to be decoded
* @len: Length of the data to be decoded
* @out_len: Pointer to output length variable
* Returns: Allocated buffer of out_len bytes of decoded data,
* or %NULL on failure. */
unsigned char *
UA_unbase64(const unsigned char *src, size_t len, size_t *out_len);
_UA_END_DECLS
#endif /* UA_BASE64_H_ */
......@@ -82,89 +82,87 @@ int __secs_to_tm(long long t, struct mytm *tm) {
return 0;
}
int __month_to_secs(int month, int is_leap)
{
static const int secs_through_month[] = {
0, 31*86400, 59*86400, 90*86400,
120*86400, 151*86400, 181*86400, 212*86400,
243*86400, 273*86400, 304*86400, 334*86400 };
int t = secs_through_month[month];
if (is_leap && month >= 2) t+=86400;
return t;
int __month_to_secs(int month, int is_leap) {
static const int secs_through_month[] =
{0, 31*86400, 59*86400, 90*86400,
120*86400, 151*86400, 181*86400, 212*86400,
243*86400, 273*86400, 304*86400, 334*86400 };
int t = secs_through_month[month];
if (is_leap && month >= 2)
t+=86400;
return t;
}
long long __year_to_secs(long long year, int *is_leap)
{
if (year-(int)2ULL <= 136) {
int y = (int)year;
int leaps = (y-68)>>2;
if (!((y-68)&3)) {
leaps--;
if (is_leap) *is_leap = 1;
} else if (is_leap) *is_leap = 0;
return 31536000*(y-70) + 86400*leaps;
}
int cycles, centuries, leaps, rem;
//if (!is_leap) is_leap = &(int){0};
int is_leap_val = 0;
if (!is_leap){
is_leap = &is_leap_val;
long long __year_to_secs(long long year, int *is_leap) {
if (year-(int)2ULL <= 136) {
long long y = (int)year;
long long leaps = (y-68)>>2;
if (!((y-8)&3)) {
leaps--;
if (is_leap) *is_leap = 1;
} else if (is_leap) *is_leap = 0;
return 31536000*(y-70) + 86400*leaps;
}
int cycles, centuries, leaps, rem;
//if (!is_leap) is_leap = &(int){0};
int is_leap_val = 0;
if (!is_leap) {
is_leap = &is_leap_val;
}
cycles = (int)((year-100) / 400);
rem = (int)((year-100) % 400);
/* Comparison is always false because rem >= 0.
if (rem < 0) {
cycles--;
rem += 400;
} */
if (!rem) {
*is_leap = 1;
centuries = 0;
leaps = 0;
} else {
if (rem >= 200) {
if (rem >= 300) centuries = 3, rem -= 300;
else centuries = 2, rem -= 200;
} else {
if (rem >= 100) centuries = 1, rem -= 100;
else centuries = 0;
}
if (!rem) {
*is_leap = 0;
leaps = 0;
} else {
leaps = (rem / (int)4U);
rem %= (int)4U;
*is_leap = !rem;
}
cycles = (int)((year-100) / 400);
rem = (int)((year-100) % 400);
/* Comparison is always false because rem >= 0.
if (rem < 0) {
cycles--;
rem += 400;
} */
if (!rem) {
*is_leap = 1;
centuries = 0;
leaps = 0;
} else {
if (rem >= 200) {
if (rem >= 300) centuries = 3, rem -= 300;
else centuries = 2, rem -= 200;
} else {
if (rem >= 100) centuries = 1, rem -= 100;
else centuries = 0;
}
if (!rem) {
*is_leap = 0;
leaps = 0;
} else {
leaps = (rem / (int)4U);
rem %= (int)4U;
*is_leap = !rem;
}
}
leaps += 97*cycles + 24*centuries - *is_leap;
return (year-100) * 31536000LL + leaps * 86400LL + 946684800 + 86400;
}
leaps += 97*cycles + 24*centuries - *is_leap;
return (year-100) * 31536000LL + leaps * 86400LL + 946684800 + 86400;
}
long long __tm_to_secs(const struct mytm *tm)
{
int is_leap;
long long year = tm->tm_year;
int month = tm->tm_mon;
if (month >= 12 || month < 0) {
int adj = month / 12;
month %= 12;
if (month < 0) {
adj--;
month += 12;
}
year += adj;
}
long long t = __year_to_secs(year, &is_leap);
t += __month_to_secs(month, is_leap);
t += 86400LL * (tm->tm_mday-1);
t += 3600LL * tm->tm_hour;
t += 60LL * tm->tm_min;
t += tm->tm_sec;
return t;
long long __tm_to_secs(const struct mytm *tm) {
int is_leap;
long long year = tm->tm_year;
int month = tm->tm_mon;
if (month >= 12 || month < 0) {
int adj = month / 12;
month %= 12;
if (month < 0) {
adj--;
month += 12;
}
year += adj;
}
long long t = __year_to_secs(year, &is_leap);
t += __month_to_secs(month, is_leap);
t += 86400LL * (tm->tm_mday-1);
t += 3600LL * tm->tm_hour;
t += 60LL * tm->tm_min;
t += tm->tm_sec;
return t;
}
......@@ -10,9 +10,6 @@ struct mytm {
int tm_year;
int tm_wday;
int tm_yday;
int tm_isdst;
/* long __tm_gmtoff; */
/* const char *__tm_zone; */
};
int __secs_to_tm(long long t, struct mytm *tm);
......
......@@ -61,6 +61,23 @@ A full list of enabled features during build time is stored in the CMake Variabl
Prebuilt packages
-----------------
Pack branches
^^^^^^^^^^^^^
Github allows you to download a specific branch as .zip package. Just using this .zip package for open62541 will likely fail:
* CMake uses ``git describe --tags`` to automatically detect the version string. The .zip package does not include any git information
* Specific options during the build stack require additional git submodules which are not inlined in the .zip
Therefore we provide packaging branches. They have the prefix `pack/` and are automatically updated to match the referenced branch.
Here are some examples:
* `pack/master.zip <https://github.com/open62541/open62541/archive/pack/master.zip>`_
* `pack/1.0.zip <https://github.com/open62541/open62541/archive/pack/1.0.zip>`_
These pack branches have inlined submodules and the version string is hardcoded. If you need to build from source but do not want to use git,
use these specific pack versions.
Prebuild binaries
^^^^^^^^^^^^^^^^^
......
......@@ -29,7 +29,7 @@ UA_CertificateVerification_Trustlist(UA_CertificateVerification *cv,
const UA_ByteString *certificateRevocationList,
size_t certificateRevocationListSize);
#if __linux__ /* Linux only so far */
#ifdef __linux__ /* Linux only so far */
UA_EXPORT UA_StatusCode
UA_CertificateVerification_CertFolders(UA_CertificateVerification *cv,
const char *trustListFolder,
......
......@@ -659,6 +659,12 @@ policyContext_newContext_sp_basic128rsa15(UA_SecurityPolicy *securityPolicy,
if(securityPolicy == NULL)
return UA_STATUSCODE_BADINTERNALERROR;
if (localPrivateKey.length == 0) {
UA_LOG_ERROR(securityPolicy->logger, UA_LOGCATEGORY_SECURITYPOLICY,
"Can not initialize security policy. Private key is empty.");
return UA_STATUSCODE_BADINVALIDARGUMENT;
}
Basic128Rsa15_PolicyContext *pc = (Basic128Rsa15_PolicyContext *)
UA_malloc(sizeof(Basic128Rsa15_PolicyContext));
securityPolicy->policyContext = (void *)pc;
......@@ -725,7 +731,7 @@ policyContext_newContext_sp_basic128rsa15(UA_SecurityPolicy *securityPolicy,
error:
UA_LOG_ERROR(securityPolicy->logger, UA_LOGCATEGORY_SECURITYPOLICY,
"Could not create securityContext");
"Could not create securityContext: %s", UA_StatusCode_name(retval));
if(securityPolicy->policyContext != NULL)
deleteMembers_sp_basic128rsa15(securityPolicy);
return retval;
......
......@@ -610,6 +610,12 @@ policyContext_newContext_sp_basic256(UA_SecurityPolicy *securityPolicy,
if(securityPolicy == NULL)
return UA_STATUSCODE_BADINTERNALERROR;
if (localPrivateKey.length == 0) {
UA_LOG_ERROR(securityPolicy->logger, UA_LOGCATEGORY_SECURITYPOLICY,
"Can not initialize security policy. Private key is empty.");
return UA_STATUSCODE_BADINVALIDARGUMENT;
}
Basic256_PolicyContext *pc = (Basic256_PolicyContext *)
UA_malloc(sizeof(Basic256_PolicyContext));
securityPolicy->policyContext = (void *)pc;
......@@ -675,7 +681,7 @@ policyContext_newContext_sp_basic256(UA_SecurityPolicy *securityPolicy,
error:
UA_LOG_ERROR(securityPolicy->logger, UA_LOGCATEGORY_SECURITYPOLICY,
"Could not create securityContext");
"Could not create securityContext: %s", UA_StatusCode_name(retval));
if(securityPolicy->policyContext != NULL)
deleteMembers_sp_basic256(securityPolicy);
return retval;
......
......@@ -650,6 +650,12 @@ policyContext_newContext_sp_basic256sha256(UA_SecurityPolicy *securityPolicy,
if(securityPolicy == NULL)
return UA_STATUSCODE_BADINTERNALERROR;
if (localPrivateKey.length == 0) {
UA_LOG_ERROR(securityPolicy->logger, UA_LOGCATEGORY_SECURITYPOLICY,
"Can not initialize security policy. Private key is empty.");
return UA_STATUSCODE_BADINVALIDARGUMENT;
}
Basic256Sha256_PolicyContext *pc = (Basic256Sha256_PolicyContext *)
UA_malloc(sizeof(Basic256Sha256_PolicyContext));
securityPolicy->policyContext = (void *)pc;
......@@ -715,7 +721,7 @@ policyContext_newContext_sp_basic256sha256(UA_SecurityPolicy *securityPolicy,
error:
UA_LOG_ERROR(securityPolicy->logger, UA_LOGCATEGORY_SECURITYPOLICY,
"Could not create securityContext");
"Could not create securityContext: %s", UA_StatusCode_name(retval));
if(securityPolicy->policyContext != NULL)
deleteMembers_sp_basic256sha256(securityPolicy);
return retval;
......
......@@ -232,28 +232,6 @@ addDefaultNetworkLayers(UA_ServerConfig *conf, UA_UInt16 portNumber,
return UA_ServerConfig_addNetworkLayerTCP(conf, portNumber, sendBufferSize, recvBufferSize);
}
static UA_StatusCode
addDiscoveryUrl(UA_ServerConfig *config, UA_UInt16 portNumber) {
config->applicationDescription.discoveryUrlsSize = 1;
UA_String *discurl = (UA_String *) UA_Array_new(1, &UA_TYPES[UA_TYPES_STRING]);
char discoveryUrlBuffer[220];
if (config->customHostname.length) {
UA_snprintf(discoveryUrlBuffer, 220, "opc.tcp://%.*s:%d/",
(int)config->customHostname.length,
config->customHostname.data,
portNumber);
} else {
char hostnameBuffer[200];
if(UA_gethostname(hostnameBuffer, 200) == 0) {
UA_snprintf(discoveryUrlBuffer, 220, "opc.tcp://%s:%d/", hostnameBuffer, portNumber);
} else {
UA_LOG_ERROR(&config->logger, UA_LOGCATEGORY_NETWORK, "Could not get the hostname");
}
}
discurl[0] = UA_String_fromChars(discoveryUrlBuffer);
config->applicationDescription.discoveryUrls = discurl;
return UA_STATUSCODE_GOOD;
}
#ifdef UA_ENABLE_WEBSOCKET_SERVER
......@@ -426,12 +404,6 @@ UA_ServerConfig_setMinimalCustomBuffer(UA_ServerConfig *config, UA_UInt16 portNu
return retval;
}
retval = addDiscoveryUrl(config, portNumber);
if (retval != UA_STATUSCODE_GOOD) {
UA_ServerConfig_clean(config);
return retval;
}
/* Allocate the SecurityPolicies */
retval = UA_ServerConfig_addSecurityPolicyNone(config, certificate);
if(retval != UA_STATUSCODE_GOOD) {
......@@ -636,12 +608,6 @@ UA_ServerConfig_setDefaultWithSecurityPolicies(UA_ServerConfig *conf,
return retval;
}
retval = addDiscoveryUrl(conf, portNumber);
if (retval != UA_STATUSCODE_GOOD) {
UA_ServerConfig_clean(conf);
return retval;
}
retval = UA_ServerConfig_addAllSecurityPolicies(conf, certificate, privateKey);
if(retval != UA_STATUSCODE_GOOD) {
UA_ServerConfig_clean(conf);
......
......@@ -63,7 +63,7 @@ typedef struct {
mbedtls_x509_crl certificateRevocationList;
} CertInfo;
#if __linux__ /* Linux only so far */
#ifdef __linux__ /* Linux only so far */
#include <dirent.h>
#include <limits.h>
......@@ -196,7 +196,7 @@ certificateVerification_verify(void *verificationContext,
if(!ci)
return UA_STATUSCODE_BADINTERNALERROR;
#if __linux__ /* Reload certificates if folder paths are specified */
#ifdef __linux__ /* Reload certificates if folder paths are specified */
reloadCertificates(ci);
#endif
......@@ -553,7 +553,7 @@ error:
return UA_STATUSCODE_BADINTERNALERROR;
}
#if __linux__ /* Linux only so far */
#ifdef __linux__ /* Linux only so far */
UA_StatusCode
UA_CertificateVerification_CertFolders(UA_CertificateVerification *cv,
......
......@@ -525,8 +525,8 @@ UA_Client_sendAsyncRequest(UA_Client *client, const void *request,
UA_UInt32 *requestId) {
if (UA_Client_getState(client) < UA_CLIENTSTATE_SECURECHANNEL) {
UA_LOG_INFO(&client->config.logger, UA_LOGCATEGORY_CLIENT,
"Cient must be connected to send high-level requests");
return UA_STATUSCODE_GOOD;
"Client must be connected to send high-level requests");
return UA_STATUSCODE_BADSERVERNOTCONNECTED;
}
return __UA_Client_AsyncService(client, request, requestType, callback,
responseType, userdata, requestId);
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment