mirror of https://github.com/FreeRDP/FreeRDP
Merge branch 'master' of github.com:awakecoding/FreeRDP into shadow
This commit is contained in:
commit
5d4f28a788
|
@ -233,9 +233,23 @@ endif()
|
|||
|
||||
if(WIN32)
|
||||
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -DUNICODE -D_UNICODE")
|
||||
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -D_WIN32_WINNT=0x0501")
|
||||
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -D_CRT_SECURE_NO_WARNINGS")
|
||||
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -DWIN32_LEAN_AND_MEAN")
|
||||
|
||||
if(NOT DEFINED CMAKE_WINDOWS_VERSION)
|
||||
set(CMAKE_WINDOWS_VERSION "WINXP")
|
||||
endif()
|
||||
|
||||
if(CMAKE_WINDOWS_VERSION STREQUAL "WINXP")
|
||||
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -DWINVER=0x0501 -DWIN32_WINNT=0x0501")
|
||||
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -DWINVER=0x0501 -DWIN32_WINNT=0x0501")
|
||||
elseif(CMAKE_WINDOWS_VERSION STREQUAL "WIN7")
|
||||
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -DWINVER=0x0601 -DWIN32_WINNT=0x0601")
|
||||
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -DWINVER=0x0601 -DWIN32_WINNT=0x0601")
|
||||
elseif(CMAKE_WINDOWS_VERSION STREQUAL "WIN8")
|
||||
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -DWINVER=0x0602 -DWIN32_WINNT=0x0602")
|
||||
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -DWINVER=0x0602 -DWIN32_WINNT=0x0602")
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if(IOS)
|
||||
|
|
|
@ -345,23 +345,15 @@ static void* audin_server_thread_func(void* arg)
|
|||
|
||||
Stream_SetPosition(s, 0);
|
||||
|
||||
if (WTSVirtualChannelRead(audin->audin_channel, 0, (PCHAR) Stream_Buffer(s),
|
||||
Stream_Capacity(s), &BytesReturned) == FALSE)
|
||||
{
|
||||
if (BytesReturned == 0)
|
||||
break;
|
||||
|
||||
Stream_EnsureRemainingCapacity(s, BytesReturned);
|
||||
|
||||
if (WTSVirtualChannelRead(audin->audin_channel, 0, (PCHAR) Stream_Buffer(s),
|
||||
Stream_Capacity(s), &BytesReturned) == FALSE)
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
WTSVirtualChannelRead(audin->audin_channel, 0, NULL, 0, &BytesReturned);
|
||||
if (BytesReturned < 1)
|
||||
continue;
|
||||
Stream_EnsureRemainingCapacity(s, BytesReturned);
|
||||
if (WTSVirtualChannelRead(audin->audin_channel, 0, (PCHAR) Stream_Buffer(s),
|
||||
Stream_Capacity(s), &BytesReturned) == FALSE)
|
||||
{
|
||||
break;
|
||||
}
|
||||
|
||||
Stream_Read_UINT8(s, MessageId);
|
||||
BytesReturned--;
|
||||
|
|
|
@ -431,15 +431,14 @@ static void* cliprdr_server_thread(void* arg)
|
|||
break;
|
||||
}
|
||||
|
||||
if (WTSVirtualChannelRead(context->priv->ChannelHandle, 0,
|
||||
WTSVirtualChannelRead(context->priv->ChannelHandle, 0, NULL, 0, &BytesReturned);
|
||||
if (BytesReturned < 1)
|
||||
continue;
|
||||
Stream_EnsureRemainingCapacity(s, BytesReturned);
|
||||
if (!WTSVirtualChannelRead(context->priv->ChannelHandle, 0,
|
||||
(PCHAR) Stream_Buffer(s), Stream_Capacity(s), &BytesReturned))
|
||||
{
|
||||
if (BytesReturned)
|
||||
Stream_Seek(s, BytesReturned);
|
||||
}
|
||||
else
|
||||
{
|
||||
Stream_EnsureRemainingCapacity(s, BytesReturned);
|
||||
break;
|
||||
}
|
||||
|
||||
if (Stream_GetPosition(s) >= CLIPRDR_HEADER_LENGTH)
|
||||
|
|
|
@ -67,15 +67,14 @@ static void* drdynvc_server_thread(void* arg)
|
|||
break;
|
||||
}
|
||||
|
||||
if (WTSVirtualChannelRead(context->priv->ChannelHandle, 0,
|
||||
WTSVirtualChannelRead(context->priv->ChannelHandle, 0, NULL, 0, &BytesReturned);
|
||||
if (BytesReturned < 1)
|
||||
continue;
|
||||
Stream_EnsureRemainingCapacity(s, BytesReturned);
|
||||
if (!WTSVirtualChannelRead(context->priv->ChannelHandle, 0,
|
||||
(PCHAR) Stream_Buffer(s), Stream_Capacity(s), &BytesReturned))
|
||||
{
|
||||
if (BytesReturned)
|
||||
Stream_Seek(s, BytesReturned);
|
||||
}
|
||||
else
|
||||
{
|
||||
Stream_EnsureRemainingCapacity(s, BytesReturned);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -21,3 +21,6 @@ if(WITH_CLIENT_CHANNELS)
|
|||
add_channel_client(${MODULE_PREFIX} ${CHANNEL_NAME})
|
||||
endif()
|
||||
|
||||
if(WITH_SERVER_CHANNELS)
|
||||
add_channel_server(${MODULE_PREFIX} ${CHANNEL_NAME})
|
||||
endif()
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
|
||||
set(OPTION_DEFAULT OFF)
|
||||
set(OPTION_CLIENT_DEFAULT ON)
|
||||
set(OPTION_SERVER_DEFAULT OFF)
|
||||
set(OPTION_SERVER_DEFAULT ON)
|
||||
|
||||
define_channel_options(NAME "echo" TYPE "dynamic"
|
||||
DESCRIPTION "Echo Virtual Channel Extension"
|
||||
|
|
|
@ -0,0 +1,36 @@
|
|||
# FreeRDP: A Remote Desktop Protocol Implementation
|
||||
# FreeRDP cmake build script
|
||||
#
|
||||
# Copyright 2012 Marc-Andre Moreau <marcandre.moreau@gmail.com>
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
define_channel_server("echo")
|
||||
|
||||
set(${MODULE_PREFIX}_SRCS
|
||||
echo_main.c)
|
||||
|
||||
add_channel_server_library(${MODULE_PREFIX} ${MODULE_NAME} ${CHANNEL_NAME} FALSE "DVCPluginEntry")
|
||||
|
||||
set_target_properties(${MODULE_NAME} PROPERTIES PREFIX "")
|
||||
|
||||
set_complex_link_libraries(VARIABLE ${MODULE_PREFIX}_LIBS
|
||||
MONOLITHIC ${MONOLITHIC_BUILD}
|
||||
MODULE freerdp
|
||||
MODULES freerdp-utils freerdp-core)
|
||||
|
||||
target_link_libraries(${MODULE_NAME} ${${MODULE_PREFIX}_LIBS})
|
||||
|
||||
install(TARGETS ${MODULE_NAME} DESTINATION ${FREERDP_ADDIN_PATH} EXPORT FreeRDPTargets)
|
||||
|
||||
set_property(TARGET ${MODULE_NAME} PROPERTY FOLDER "Channels/${CHANNEL_NAME}/Server")
|
|
@ -0,0 +1,233 @@
|
|||
/**
|
||||
* FreeRDP: A Remote Desktop Protocol Implementation
|
||||
* Echo Virtual Channel Extension
|
||||
*
|
||||
* Copyright 2014 Vic Lee
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
#include "config.h"
|
||||
#endif
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#include <winpr/crt.h>
|
||||
#include <winpr/synch.h>
|
||||
#include <winpr/thread.h>
|
||||
#include <winpr/stream.h>
|
||||
|
||||
#include <freerdp/server/echo.h>
|
||||
|
||||
typedef struct _echo_server
|
||||
{
|
||||
echo_server_context context;
|
||||
|
||||
BOOL opened;
|
||||
|
||||
HANDLE stopEvent;
|
||||
|
||||
HANDLE thread;
|
||||
void* echo_channel;
|
||||
|
||||
DWORD SessionId;
|
||||
|
||||
} echo_server;
|
||||
|
||||
static BOOL echo_server_open_channel(echo_server* echo)
|
||||
{
|
||||
DWORD Error;
|
||||
HANDLE hEvent;
|
||||
DWORD StartTick;
|
||||
DWORD BytesReturned = 0;
|
||||
PULONG pSessionId = NULL;
|
||||
|
||||
if (WTSQuerySessionInformationA(echo->context.vcm, WTS_CURRENT_SESSION,
|
||||
WTSSessionId, (LPSTR*) &pSessionId, &BytesReturned) == FALSE)
|
||||
{
|
||||
return FALSE;
|
||||
}
|
||||
echo->SessionId = (DWORD) *pSessionId;
|
||||
WTSFreeMemory(pSessionId);
|
||||
|
||||
hEvent = WTSVirtualChannelManagerGetEventHandle(echo->context.vcm);
|
||||
StartTick = GetTickCount();
|
||||
|
||||
while (echo->echo_channel == NULL)
|
||||
{
|
||||
WaitForSingleObject(hEvent, 1000);
|
||||
|
||||
echo->echo_channel = WTSVirtualChannelOpenEx(echo->SessionId,
|
||||
"ECHO", WTS_CHANNEL_OPTION_DYNAMIC);
|
||||
|
||||
if (echo->echo_channel)
|
||||
break;
|
||||
|
||||
Error = GetLastError();
|
||||
if (Error == ERROR_NOT_FOUND)
|
||||
break;
|
||||
|
||||
if (GetTickCount() - StartTick > 5000)
|
||||
break;
|
||||
}
|
||||
|
||||
return echo->echo_channel ? TRUE : FALSE;
|
||||
}
|
||||
|
||||
static void* echo_server_thread_func(void* arg)
|
||||
{
|
||||
wStream* s;
|
||||
void* buffer;
|
||||
DWORD nCount;
|
||||
HANDLE events[8];
|
||||
BOOL ready = FALSE;
|
||||
HANDLE ChannelEvent;
|
||||
DWORD BytesReturned = 0;
|
||||
echo_server* echo = (echo_server*) arg;
|
||||
|
||||
if (echo_server_open_channel(echo) == FALSE)
|
||||
{
|
||||
IFCALL(echo->context.OpenResult, &echo->context, ECHO_SERVER_OPEN_RESULT_NOTSUPPORTED);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
buffer = NULL;
|
||||
BytesReturned = 0;
|
||||
ChannelEvent = NULL;
|
||||
|
||||
if (WTSVirtualChannelQuery(echo->echo_channel, WTSVirtualEventHandle, &buffer, &BytesReturned) == TRUE)
|
||||
{
|
||||
if (BytesReturned == sizeof(HANDLE))
|
||||
CopyMemory(&ChannelEvent, buffer, sizeof(HANDLE));
|
||||
|
||||
WTSFreeMemory(buffer);
|
||||
}
|
||||
|
||||
nCount = 0;
|
||||
events[nCount++] = echo->stopEvent;
|
||||
events[nCount++] = ChannelEvent;
|
||||
|
||||
/* Wait for the client to confirm that the Graphics Pipeline dynamic channel is ready */
|
||||
|
||||
while (1)
|
||||
{
|
||||
if (WaitForMultipleObjects(nCount, events, FALSE, 100) == WAIT_OBJECT_0)
|
||||
{
|
||||
IFCALL(echo->context.OpenResult, &echo->context, ECHO_SERVER_OPEN_RESULT_CLOSED);
|
||||
break;
|
||||
}
|
||||
|
||||
if (WTSVirtualChannelQuery(echo->echo_channel, WTSVirtualChannelReady, &buffer, &BytesReturned) == FALSE)
|
||||
{
|
||||
IFCALL(echo->context.OpenResult, &echo->context, ECHO_SERVER_OPEN_RESULT_ERROR);
|
||||
break;
|
||||
}
|
||||
|
||||
ready = *((BOOL*) buffer);
|
||||
|
||||
WTSFreeMemory(buffer);
|
||||
|
||||
if (ready)
|
||||
{
|
||||
IFCALL(echo->context.OpenResult, &echo->context, ECHO_SERVER_OPEN_RESULT_OK);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
s = Stream_New(NULL, 4096);
|
||||
|
||||
while (ready)
|
||||
{
|
||||
if (WaitForMultipleObjects(nCount, events, FALSE, INFINITE) == WAIT_OBJECT_0)
|
||||
break;
|
||||
|
||||
Stream_SetPosition(s, 0);
|
||||
|
||||
WTSVirtualChannelRead(echo->echo_channel, 0, NULL, 0, &BytesReturned);
|
||||
if (BytesReturned < 1)
|
||||
continue;
|
||||
Stream_EnsureRemainingCapacity(s, BytesReturned);
|
||||
if (WTSVirtualChannelRead(echo->echo_channel, 0, (PCHAR) Stream_Buffer(s),
|
||||
(ULONG) Stream_Capacity(s), &BytesReturned) == FALSE)
|
||||
{
|
||||
break;
|
||||
}
|
||||
|
||||
IFCALL(echo->context.Response, &echo->context, (PCHAR) Stream_Buffer(s), BytesReturned);
|
||||
}
|
||||
|
||||
Stream_Free(s, TRUE);
|
||||
WTSVirtualChannelClose(echo->echo_channel);
|
||||
echo->echo_channel = NULL;
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static void echo_server_open(echo_server_context* context)
|
||||
{
|
||||
echo_server* echo = (echo_server*) context;
|
||||
|
||||
if (echo->thread == NULL)
|
||||
{
|
||||
echo->stopEvent = CreateEvent(NULL, TRUE, FALSE, NULL);
|
||||
echo->thread = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE) echo_server_thread_func, (void*) echo, 0, NULL);
|
||||
}
|
||||
}
|
||||
|
||||
static void echo_server_close(echo_server_context* context)
|
||||
{
|
||||
echo_server* echo = (echo_server*) context;
|
||||
|
||||
if (echo->thread)
|
||||
{
|
||||
SetEvent(echo->stopEvent);
|
||||
WaitForSingleObject(echo->thread, INFINITE);
|
||||
CloseHandle(echo->thread);
|
||||
CloseHandle(echo->stopEvent);
|
||||
echo->thread = NULL;
|
||||
echo->stopEvent = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
static BOOL echo_server_request(echo_server_context* context, const BYTE* buffer, UINT32 length)
|
||||
{
|
||||
echo_server* echo = (echo_server*) context;
|
||||
|
||||
return WTSVirtualChannelWrite(echo->echo_channel, (PCHAR) buffer, length, NULL);
|
||||
}
|
||||
|
||||
echo_server_context* echo_server_context_new(HANDLE vcm)
|
||||
{
|
||||
echo_server* echo;
|
||||
|
||||
echo = (echo_server*) calloc(1, sizeof(echo_server));
|
||||
|
||||
echo->context.vcm = vcm;
|
||||
echo->context.Open = echo_server_open;
|
||||
echo->context.Close = echo_server_close;
|
||||
echo->context.Request = echo_server_request;
|
||||
|
||||
return (echo_server_context*) echo;
|
||||
}
|
||||
|
||||
void echo_server_context_free(echo_server_context* context)
|
||||
{
|
||||
echo_server* echo = (echo_server*) context;
|
||||
|
||||
echo_server_close(context);
|
||||
|
||||
free(echo);
|
||||
}
|
|
@ -173,15 +173,14 @@ static void* encomsp_server_thread(void* arg)
|
|||
break;
|
||||
}
|
||||
|
||||
if (WTSVirtualChannelRead(context->priv->ChannelHandle, 0,
|
||||
WTSVirtualChannelRead(context->priv->ChannelHandle, 0, NULL, 0, &BytesReturned);
|
||||
if (BytesReturned < 1)
|
||||
continue;
|
||||
Stream_EnsureRemainingCapacity(s, BytesReturned);
|
||||
if (!WTSVirtualChannelRead(context->priv->ChannelHandle, 0,
|
||||
(PCHAR) Stream_Buffer(s), Stream_Capacity(s), &BytesReturned))
|
||||
{
|
||||
if (BytesReturned)
|
||||
Stream_Seek(s, BytesReturned);
|
||||
}
|
||||
else
|
||||
{
|
||||
Stream_EnsureRemainingCapacity(s, BytesReturned);
|
||||
break;
|
||||
}
|
||||
|
||||
if (Stream_GetPosition(s) >= ENCOMSP_ORDER_HEADER_SIZE)
|
||||
|
|
|
@ -598,15 +598,14 @@ static void* rdpdr_server_thread(void* arg)
|
|||
break;
|
||||
}
|
||||
|
||||
if (WTSVirtualChannelRead(context->priv->ChannelHandle, 0, (PCHAR) Stream_Pointer(s),
|
||||
Stream_Capacity(s) - Stream_GetPosition(s), &BytesReturned))
|
||||
{
|
||||
if (BytesReturned)
|
||||
Stream_Seek(s, BytesReturned);
|
||||
}
|
||||
else
|
||||
{
|
||||
WTSVirtualChannelRead(context->priv->ChannelHandle, 0, NULL, 0, &BytesReturned);
|
||||
if (BytesReturned < 1)
|
||||
continue;
|
||||
Stream_EnsureRemainingCapacity(s, BytesReturned);
|
||||
if (!WTSVirtualChannelRead(context->priv->ChannelHandle, 0,
|
||||
(PCHAR) Stream_Buffer(s), Stream_Capacity(s), &BytesReturned))
|
||||
{
|
||||
break;
|
||||
}
|
||||
|
||||
if (Stream_GetPosition(s) >= RDPDR_HEADER_LENGTH)
|
||||
|
|
|
@ -626,7 +626,7 @@ BOOL rdpsnd_server_handle_messages(RdpsndServerContext *context)
|
|||
RdpsndServerPrivate *priv = context->priv;
|
||||
wStream *s = priv->input_stream;
|
||||
|
||||
if (!WTSVirtualChannelRead(priv->channelEvent, 0, (PCHAR)Stream_Pointer(s), priv->expectedBytes, &bytesReturned))
|
||||
if (!WTSVirtualChannelRead(priv->ChannelHandle, 0, (PCHAR)Stream_Pointer(s), priv->expectedBytes, &bytesReturned))
|
||||
{
|
||||
if (GetLastError() == ERROR_NO_DATA)
|
||||
return TRUE;
|
||||
|
|
|
@ -43,6 +43,7 @@
|
|||
#include <freerdp/server/audin.h>
|
||||
#include <freerdp/server/rdpsnd.h>
|
||||
#include <freerdp/server/cliprdr.h>
|
||||
#include <freerdp/server/echo.h>
|
||||
#include <freerdp/server/rdpdr.h>
|
||||
#include <freerdp/server/drdynvc.h>
|
||||
|
||||
|
@ -57,6 +58,9 @@ void freerdp_channels_dummy()
|
|||
cliprdr_server_context_new(NULL);
|
||||
cliprdr_server_context_free(NULL);
|
||||
|
||||
echo_server_context_new(NULL);
|
||||
echo_server_context_free(NULL);
|
||||
|
||||
rdpdr_server_context_new(NULL);
|
||||
rdpdr_server_context_free(NULL);
|
||||
|
||||
|
|
|
@ -62,10 +62,21 @@ else()
|
|||
endif()
|
||||
|
||||
set(APPCOMPAT_DIR "${CMAKE_CURRENT_BINARY_DIR}/appcompat_v7")
|
||||
set(supportdir "${ANDROID_SDK}/extras/android/support/v7/appcompat")
|
||||
set(compatibilitydir "${ANDROID_SDK}/extras/android/compatibility/v7/appcompat")
|
||||
if(EXISTS "${supportdir}" AND IS_DIRECTORY "${supportdir}")
|
||||
add_custom_target(copy_appcompat ALL
|
||||
COMMAND ${CMAKE_COMMAND} -E copy_directory ${ANDROID_SDK}/extras/android/support/v7/appcompat ${APPCOMPAT_DIR}
|
||||
COMMAND ${CMAKE_COMMAND} -E copy_directory "${supportdir}" ${APPCOMPAT_DIR}
|
||||
COMMAND ${ANDROID_COMMAND} update lib-project -p ${APPCOMPAT_DIR}
|
||||
)
|
||||
elseif(EXISTS "${compatibilitydir}" AND IS_DIRECTORY "${compatibilitydir}")
|
||||
add_custom_target(copy_appcompat ALL
|
||||
COMMAND ${CMAKE_COMMAND} -E copy_directory "${compatibilitydir}" ${APPCOMPAT_DIR}
|
||||
COMMAND ${ANDROID_COMMAND} update lib-project -p ${APPCOMPAT_DIR}
|
||||
)
|
||||
else()
|
||||
message( FATAL_ERROR "${ANDROID_SDK}/extras/android/{support|compatibility}/v7/appcompat directory not found. Please install a recent version of Android Support Library, CMake will now exit." )
|
||||
endif()
|
||||
|
||||
add_subdirectory(FreeRDPCore)
|
||||
add_subdirectory(aFreeRDP)
|
||||
|
|
|
@ -11,15 +11,20 @@
|
|||
-->
|
||||
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
>
|
||||
android:layout_height="match_parent" >
|
||||
|
||||
<!-- Dummy item to prevent SuperBarView from receiving focus (and showing the keyboard) -->
|
||||
<LinearLayout
|
||||
android:focusable="true" android:focusableInTouchMode="true"
|
||||
android:layout_width="0px" android:layout_height="0px"/>
|
||||
|
||||
<include android:id="@+id/superBar" layout="@layout/super_bar" android:layout_alignParentTop="true" />
|
||||
<LinearLayout
|
||||
android:layout_width="0px"
|
||||
android:layout_height="0px"
|
||||
android:focusable="true"
|
||||
android:focusableInTouchMode="true" />
|
||||
|
||||
<include
|
||||
android:id="@+id/superBar"
|
||||
android:layout_alignParentTop="true"
|
||||
layout="@layout/super_bar" />
|
||||
|
||||
<ListView
|
||||
android:id="@+id/listViewBookmarks"
|
||||
|
@ -27,16 +32,6 @@
|
|||
android:layout_height="match_parent"
|
||||
android:layout_below="@id/superBar"
|
||||
android:divider="@android:drawable/divider_horizontal_dark"
|
||||
android:dividerHeight="1dp"
|
||||
android:visibility="gone"
|
||||
/>
|
||||
|
||||
<WebView
|
||||
android:id="@+id/webViewWelcome"
|
||||
android:layout_height="match_parent"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_below="@id/superBar"
|
||||
android:fillViewport="true"
|
||||
/>
|
||||
android:dividerHeight="1dp" />
|
||||
|
||||
</RelativeLayout>
|
|
@ -9,26 +9,12 @@
|
|||
|
||||
package com.freerdp.freerdpcore.presentation;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Locale;
|
||||
|
||||
import com.freerdp.freerdpcore.R;
|
||||
import com.freerdp.freerdpcore.application.GlobalApp;
|
||||
import com.freerdp.freerdpcore.application.GlobalSettings;
|
||||
import com.freerdp.freerdpcore.domain.BookmarkBase;
|
||||
import com.freerdp.freerdpcore.domain.ConnectionReference;
|
||||
import com.freerdp.freerdpcore.domain.PlaceholderBookmark;
|
||||
import com.freerdp.freerdpcore.domain.QuickConnectBookmark;
|
||||
import com.freerdp.freerdpcore.utils.BookmarkArrayAdapter;
|
||||
import com.freerdp.freerdpcore.utils.SeparatedListAdapter;
|
||||
|
||||
import android.app.Activity;
|
||||
import android.app.AlertDialog;
|
||||
import android.content.DialogInterface;
|
||||
import android.content.Intent;
|
||||
import android.content.res.Configuration;
|
||||
import android.net.Uri;
|
||||
import android.os.Bundle;
|
||||
import android.text.Editable;
|
||||
|
@ -42,8 +28,6 @@ import android.view.MenuItem;
|
|||
import android.view.View;
|
||||
import android.view.View.OnClickListener;
|
||||
import android.view.View.OnCreateContextMenuListener;
|
||||
import android.webkit.WebView;
|
||||
import android.webkit.WebViewClient;
|
||||
import android.widget.AdapterView;
|
||||
import android.widget.AdapterView.AdapterContextMenuInfo;
|
||||
import android.widget.Button;
|
||||
|
@ -51,6 +35,16 @@ import android.widget.CheckBox;
|
|||
import android.widget.EditText;
|
||||
import android.widget.ListView;
|
||||
|
||||
import com.freerdp.freerdpcore.R;
|
||||
import com.freerdp.freerdpcore.application.GlobalApp;
|
||||
import com.freerdp.freerdpcore.application.GlobalSettings;
|
||||
import com.freerdp.freerdpcore.domain.BookmarkBase;
|
||||
import com.freerdp.freerdpcore.domain.ConnectionReference;
|
||||
import com.freerdp.freerdpcore.domain.PlaceholderBookmark;
|
||||
import com.freerdp.freerdpcore.domain.QuickConnectBookmark;
|
||||
import com.freerdp.freerdpcore.utils.BookmarkArrayAdapter;
|
||||
import com.freerdp.freerdpcore.utils.SeparatedListAdapter;
|
||||
|
||||
public class HomeActivity extends Activity {
|
||||
private final static String ADD_BOOKMARK_PLACEHOLDER = "add_bookmark";
|
||||
|
||||
|
@ -108,22 +102,6 @@ public class HomeActivity extends Activity {
|
|||
|
||||
listViewBookmarks = (ListView) findViewById(R.id.listViewBookmarks);
|
||||
|
||||
String filename = ((getResources().getConfiguration().screenLayout & Configuration.SCREENLAYOUT_SIZE_MASK) >= Configuration.SCREENLAYOUT_SIZE_LARGE) ? "welcome.html" : "welcome_phone.html";
|
||||
Locale def = Locale.getDefault();
|
||||
String prefix = def.getLanguage().toLowerCase(def);
|
||||
|
||||
String base = "file:///android_asset/";
|
||||
String dir = prefix + "_help_page/"
|
||||
+ filename;
|
||||
try {
|
||||
InputStream is = getAssets().open(dir);
|
||||
is.close();
|
||||
dir = base + dir;
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Missing localized asset " + dir, e);
|
||||
dir = "file:///android_asset/help_page/" + filename;
|
||||
}
|
||||
|
||||
// set listeners for the list view
|
||||
listViewBookmarks.setOnItemClickListener(new AdapterView.OnItemClickListener() {
|
||||
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
# Copyright (c) 2010-2011, Ethan Rublee
|
||||
# Copyright (c) 2011-2013, Andrey Kamaev
|
||||
# Copyright (c) 2011-2014, Andrey Kamaev
|
||||
# All rights reserved.
|
||||
#
|
||||
# Redistribution and use in source and binary forms, with or without
|
||||
|
@ -12,9 +12,9 @@
|
|||
# this list of conditions and the following disclaimer in the documentation
|
||||
# and/or other materials provided with the distribution.
|
||||
#
|
||||
# 3. The name of the copyright holders may be used to endorse or promote
|
||||
# products derived from this software without specific prior written
|
||||
# permission.
|
||||
# 3. Neither the name of the copyright holder nor the names of its
|
||||
# contributors may be used to endorse or promote products derived from this
|
||||
# software without specific prior written permission.
|
||||
#
|
||||
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
# AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
|
@ -29,7 +29,7 @@
|
|||
# POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
# ------------------------------------------------------------------------------
|
||||
# Android CMake toolchain file, for use with the Android NDK r5-r8
|
||||
# Android CMake toolchain file, for use with the Android NDK r5-r9
|
||||
# Requires cmake 2.6.3 or newer (2.8.5 or newer is recommended).
|
||||
# See home page: https://github.com/taka-no-me/android-cmake
|
||||
#
|
||||
|
@ -87,8 +87,7 @@
|
|||
# "armeabi-v6 with VFP" - tuned for ARMv6 processors having VFP.
|
||||
# "x86" - matches to the NDK ABI with the same name.
|
||||
# See ${ANDROID_NDK}/docs/CPU-ARCH-ABIS.html for the documentation.
|
||||
# "mips" - matches to the NDK ABI with the same name
|
||||
# (It is not tested on real devices by the authos of this toolchain)
|
||||
# "mips" - matches to the NDK ABI with the same name.
|
||||
# See ${ANDROID_NDK}/docs/CPU-ARCH-ABIS.html for the documentation.
|
||||
#
|
||||
# ANDROID_NATIVE_API_LEVEL=android-8 - level of Android API compile for.
|
||||
|
@ -294,6 +293,16 @@
|
|||
# [~] automatically detect if explicit link to crtbegin_*.o is needed
|
||||
# - June 2013
|
||||
# [~] fixed stl include path for standalone toolchain made by NDK >= r8c
|
||||
# - July 2013
|
||||
# [+] updated for NDK r9
|
||||
# - November 2013
|
||||
# [+] updated for NDK r9b
|
||||
# - December 2013
|
||||
# [+] updated for NDK r9c
|
||||
# - January 2014
|
||||
# [~] fix copying of shared STL
|
||||
# - April 2014
|
||||
# [+] updated for NDK r9d
|
||||
# ------------------------------------------------------------------------------
|
||||
|
||||
cmake_minimum_required( VERSION 2.6.3 )
|
||||
|
@ -326,7 +335,7 @@ endif()
|
|||
# rpath makes low sence for Android
|
||||
set( CMAKE_SKIP_RPATH TRUE CACHE BOOL "If set, runtime paths are not added when using shared libraries." )
|
||||
|
||||
set( ANDROID_SUPPORTED_NDK_VERSIONS ${ANDROID_EXTRA_NDK_VERSIONS} -r9b -r9 -r8e -r8d -r8c -r8b -r8 -r7c -r7b -r7 -r6b -r6 -r5c -r5b -r5 "" )
|
||||
set( ANDROID_SUPPORTED_NDK_VERSIONS ${ANDROID_EXTRA_NDK_VERSIONS} -r9d -r9c -r9b -r9 -r8e -r8d -r8c -r8b -r8 -r7c -r7b -r7 -r6b -r6 -r5c -r5b -r5 "" )
|
||||
if(NOT DEFINED ANDROID_NDK_SEARCH_PATHS)
|
||||
if( CMAKE_HOST_WIN32 )
|
||||
file( TO_CMAKE_PATH "$ENV{PROGRAMFILES}" ANDROID_NDK_SEARCH_PATHS )
|
||||
|
@ -470,10 +479,9 @@ if( ANDROID_FORBID_SYGWIN )
|
|||
endif()
|
||||
endif()
|
||||
|
||||
# FIXME: properly detect 64-bit host, currently reported as 32-bit
|
||||
|
||||
# detect current host platform
|
||||
if( NOT DEFINED ANDROID_NDK_HOST_X64 AND CMAKE_HOST_SYSTEM_PROCESSOR MATCHES "amd64|x86_64|AMD64")
|
||||
if( NOT DEFINED ANDROID_NDK_HOST_X64 AND (CMAKE_HOST_SYSTEM_PROCESSOR MATCHES "amd64|x86_64|AMD64" OR CMAKE_HOST_APPLE) )
|
||||
set( ANDROID_NDK_HOST_X64 1 CACHE BOOL "Try to use 64-bit compiler toolchain" )
|
||||
mark_as_advanced( ANDROID_NDK_HOST_X64 )
|
||||
endif()
|
||||
|
@ -494,7 +502,7 @@ else()
|
|||
endif()
|
||||
|
||||
if( NOT ANDROID_NDK_HOST_X64 )
|
||||
#set( ANDROID_NDK_HOST_SYSTEM_NAME ${ANDROID_NDK_HOST_SYSTEM_NAME2} )
|
||||
set( ANDROID_NDK_HOST_SYSTEM_NAME ${ANDROID_NDK_HOST_SYSTEM_NAME2} )
|
||||
endif()
|
||||
|
||||
# see if we have path to Android NDK
|
||||
|
@ -1139,15 +1147,7 @@ endif()
|
|||
# case of shared STL linkage
|
||||
if( ANDROID_STL MATCHES "shared" AND DEFINED __libstl )
|
||||
string( REPLACE "_static.a" "_shared.so" __libstl "${__libstl}" )
|
||||
if( NOT _CMAKE_IN_TRY_COMPILE AND __libstl MATCHES "[.]so$" )
|
||||
get_filename_component( __libstlname "${__libstl}" NAME )
|
||||
execute_process( COMMAND "${CMAKE_COMMAND}" -E copy_if_different "${__libstl}" "${LIBRARY_OUTPUT_PATH}/${__libstlname}" RESULT_VARIABLE __fileCopyProcess )
|
||||
if( NOT __fileCopyProcess EQUAL 0 OR NOT EXISTS "${LIBRARY_OUTPUT_PATH}/${__libstlname}")
|
||||
message( SEND_ERROR "Failed copying of ${__libstl} to the ${LIBRARY_OUTPUT_PATH}/${__libstlname}" )
|
||||
endif()
|
||||
unset( __fileCopyProcess )
|
||||
unset( __libstlname )
|
||||
endif()
|
||||
# TODO: check if .so file exists before the renaming
|
||||
endif()
|
||||
|
||||
|
||||
|
@ -1512,7 +1512,8 @@ endif()
|
|||
|
||||
# global includes and link directories
|
||||
include_directories( SYSTEM "${ANDROID_SYSROOT}/usr/include" ${ANDROID_STL_INCLUDE_DIRS} )
|
||||
link_directories( "${CMAKE_INSTALL_PREFIX}/libs/${ANDROID_NDK_ABI_NAME}" )
|
||||
get_filename_component(__android_install_path "${CMAKE_INSTALL_PREFIX}/libs/${ANDROID_NDK_ABI_NAME}" ABSOLUTE) # avoid CMP0015 policy warning
|
||||
link_directories( "${__android_install_path}" )
|
||||
|
||||
# detect if need link crtbegin_so.o explicitly
|
||||
if( NOT DEFINED ANDROID_EXPLICIT_CRT_LINK )
|
||||
|
@ -1564,6 +1565,18 @@ if(NOT _CMAKE_IN_TRY_COMPILE)
|
|||
set( LIBRARY_OUTPUT_PATH "${LIBRARY_OUTPUT_PATH_ROOT}/libs/${ANDROID_NDK_ABI_NAME}" CACHE PATH "path for android libs" )
|
||||
endif()
|
||||
|
||||
# copy shaed stl library to build directory
|
||||
if( NOT _CMAKE_IN_TRY_COMPILE AND __libstl MATCHES "[.]so$" )
|
||||
get_filename_component( __libstlname "${__libstl}" NAME )
|
||||
execute_process( COMMAND "${CMAKE_COMMAND}" -E copy_if_different "${__libstl}" "${LIBRARY_OUTPUT_PATH}/${__libstlname}" RESULT_VARIABLE __fileCopyProcess )
|
||||
if( NOT __fileCopyProcess EQUAL 0 OR NOT EXISTS "${LIBRARY_OUTPUT_PATH}/${__libstlname}")
|
||||
message( SEND_ERROR "Failed copying of ${__libstl} to the ${LIBRARY_OUTPUT_PATH}/${__libstlname}" )
|
||||
endif()
|
||||
unset( __fileCopyProcess )
|
||||
unset( __libstlname )
|
||||
endif()
|
||||
|
||||
|
||||
# set these global flags for cmake client scripts to change behavior
|
||||
set( ANDROID True )
|
||||
set( BUILD_ANDROID True )
|
||||
|
@ -1672,6 +1685,19 @@ if( NOT PROJECT_NAME STREQUAL "CMAKE_TRY_COMPILE" )
|
|||
endif()
|
||||
|
||||
|
||||
# force cmake to produce / instead of \ in build commands for Ninja generator
|
||||
if( CMAKE_GENERATOR MATCHES "Ninja" AND CMAKE_HOST_WIN32 )
|
||||
# it is a bad hack after all
|
||||
# CMake generates Ninja makefiles with UNIX paths only if it thinks that we are going to build with MinGW
|
||||
set( CMAKE_COMPILER_IS_MINGW TRUE ) # tell CMake that we are MinGW
|
||||
set( CMAKE_CROSSCOMPILING TRUE ) # stop recursion
|
||||
enable_language( C )
|
||||
enable_language( CXX )
|
||||
# unset( CMAKE_COMPILER_IS_MINGW ) # can't unset because CMake does not convert back-slashes in response files without it
|
||||
unset( MINGW )
|
||||
endif()
|
||||
|
||||
|
||||
# set some obsolete variables for backward compatibility
|
||||
set( ANDROID_SET_OBSOLETE_VARIABLES ON CACHE BOOL "Define obsolete Andrid-specific cmake variables" )
|
||||
mark_as_advanced( ANDROID_SET_OBSOLETE_VARIABLES )
|
||||
|
@ -1726,7 +1752,7 @@ endif()
|
|||
# BUILD_WITH_STANDALONE_TOOLCHAIN : TRUE if standalone toolchain is used
|
||||
# ANDROID_NDK_HOST_SYSTEM_NAME : "windows", "linux-x86" or "darwin-x86" depending on host platform
|
||||
# ANDROID_NDK_ABI_NAME : "armeabi", "armeabi-v7a", "x86" or "mips" depending on ANDROID_ABI
|
||||
# ANDROID_NDK_RELEASE : one of r5, r5b, r5c, r6, r6b, r7, r7b, r7c, r8, r8b, r8c, r8d, r8e; set only for NDK
|
||||
# ANDROID_NDK_RELEASE : one of r5, r5b, r5c, r6, r6b, r7, r7b, r7c, r8, r8b, r8c, r8d, r8e, r9, r9b, r9c, r9d; set only for NDK
|
||||
# ANDROID_ARCH_NAME : "arm" or "x86" or "mips" depending on ANDROID_ABI
|
||||
# ANDROID_SYSROOT : path to the compiler sysroot
|
||||
# TOOL_OS_SUFFIX : "" or ".exe" depending on host platform
|
||||
|
|
|
@ -212,12 +212,14 @@ enum RDPDR_PRINTER_ANNOUNCE_FLAG
|
|||
|
||||
/* [MS-FSCC] FSCTL Structures */
|
||||
|
||||
#if !defined(_WIN32) || (defined(_WIN32) && (_WIN32_WINNT < 0x0600))
|
||||
#define FSCTL_LMR_SET_LINK_TRACKING_INFORMATION 0x1400ec
|
||||
#define FSCTL_PIPE_PEEK 0x11400c
|
||||
#define FSCTL_PIPE_TRANSCEIVE 0x11c017
|
||||
#define FSCTL_PIPE_WAIT 0x110018
|
||||
#define FSCTL_QUERY_ON_DISK_VOLUME_INFO 0x9013c
|
||||
#define FSCTL_QUERY_SPARING_INFO 0x90138
|
||||
#endif
|
||||
|
||||
#ifndef _WIN32
|
||||
#define FSCTL_CREATE_OR_GET_OBJECT_ID 0x900c0
|
||||
|
@ -239,8 +241,10 @@ enum RDPDR_PRINTER_ANNOUNCE_FLAG
|
|||
#define FSCTL_WRITE_USN_CLOSE_RECORD 0x900ef
|
||||
#endif
|
||||
|
||||
#if !defined(_WIN32) || (defined(_WIN32) && (_WIN32_WINNT < 0x0600))
|
||||
#define FSCTL_SET_DEFECT_MANAGEMENT 0x98134
|
||||
#define FSCTL_SET_ZERO_ON_DEALLOCATION 0x90194
|
||||
#endif
|
||||
|
||||
/* [MS-FSCC] FileFsAttributeInformation.FileSystemAttributes */
|
||||
|
||||
|
|
|
@ -0,0 +1,85 @@
|
|||
/**
|
||||
* FreeRDP: A Remote Desktop Protocol Implementation
|
||||
* Echo Virtual Channel Extension
|
||||
*
|
||||
* Copyright 2014 Vic Lee
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef FREERDP_CHANNEL_ECHO_SERVER_H
|
||||
#define FREERDP_CHANNEL_ECHO_SERVER_H
|
||||
|
||||
#include <freerdp/channels/wtsvc.h>
|
||||
|
||||
typedef enum ECHO_SERVER_OPEN_RESULT
|
||||
{
|
||||
ECHO_SERVER_OPEN_RESULT_OK = 0,
|
||||
ECHO_SERVER_OPEN_RESULT_CLOSED = 1,
|
||||
ECHO_SERVER_OPEN_RESULT_NOTSUPPORTED = 2,
|
||||
ECHO_SERVER_OPEN_RESULT_ERROR = 3
|
||||
} ECHO_SERVER_OPEN_RESULT;
|
||||
|
||||
typedef struct _echo_server_context echo_server_context;
|
||||
|
||||
typedef void (*psEchoServerOpen)(echo_server_context* context);
|
||||
typedef void (*psEchoServerClose)(echo_server_context* context);
|
||||
typedef BOOL (*psEchoServerRequest)(echo_server_context* context, const BYTE* buffer, UINT32 length);
|
||||
|
||||
typedef void (*psEchoServerOpenResult)(echo_server_context* context, ECHO_SERVER_OPEN_RESULT result);
|
||||
typedef void (*psEchoServerResponse)(echo_server_context* context, const BYTE* buffer, UINT32 length);
|
||||
|
||||
struct _echo_server_context
|
||||
{
|
||||
HANDLE vcm;
|
||||
|
||||
/* Server self-defined pointer. */
|
||||
void* data;
|
||||
|
||||
/*** APIs called by the server. ***/
|
||||
/**
|
||||
* Open the echo channel.
|
||||
*/
|
||||
psEchoServerOpen Open;
|
||||
/**
|
||||
* Close the echo channel.
|
||||
*/
|
||||
psEchoServerClose Close;
|
||||
/**
|
||||
* Send echo request PDU.
|
||||
*/
|
||||
psEchoServerRequest Request;
|
||||
|
||||
/*** Callbacks registered by the server. ***/
|
||||
/**
|
||||
* Indicate whether the channel is opened successfully.
|
||||
*/
|
||||
psEchoServerOpenResult OpenResult;
|
||||
/**
|
||||
* Receive echo response PDU.
|
||||
*/
|
||||
psEchoServerResponse Response;
|
||||
};
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
FREERDP_API echo_server_context* echo_server_context_new(HANDLE vcm);
|
||||
FREERDP_API void echo_server_context_free(echo_server_context* context);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* FREERDP_CHANNEL_ECHO_SERVER_H */
|
|
@ -42,6 +42,15 @@
|
|||
#define DEBUG_DVC(fmt, ...) DEBUG_NULL(fmt, ## __VA_ARGS__)
|
||||
#endif
|
||||
|
||||
struct _wtsChannelMessage
|
||||
{
|
||||
UINT16 channelId;
|
||||
UINT16 reserved;
|
||||
UINT32 length;
|
||||
UINT32 offset;
|
||||
};
|
||||
typedef struct _wtsChannelMessage wtsChannelMessage;
|
||||
|
||||
static DWORD g_SessionId = 1;
|
||||
static wHashTable* g_ServerHandles = NULL;
|
||||
|
||||
|
@ -75,15 +84,16 @@ static rdpPeerChannel* wts_get_dvc_channel_by_id(WTSVirtualChannelManager* vcm,
|
|||
static void wts_queue_receive_data(rdpPeerChannel* channel, const BYTE* Buffer, UINT32 Length)
|
||||
{
|
||||
BYTE* buffer;
|
||||
UINT32 length;
|
||||
UINT16 channelId;
|
||||
wtsChannelMessage* messageCtx;
|
||||
|
||||
length = Length;
|
||||
buffer = (BYTE*) malloc(length);
|
||||
CopyMemory(buffer, Buffer, length);
|
||||
channelId = channel->channelId;
|
||||
messageCtx = (wtsChannelMessage*) malloc(sizeof(wtsChannelMessage) + Length);
|
||||
messageCtx->channelId = channel->channelId;
|
||||
messageCtx->length = Length;
|
||||
messageCtx->offset = 0;
|
||||
buffer = (BYTE*) (messageCtx + 1);
|
||||
CopyMemory(buffer, Buffer, Length);
|
||||
|
||||
MessageQueue_Post(channel->queue, (void*) (UINT_PTR) channelId, 0, (void*) buffer, (void*) (UINT_PTR) length);
|
||||
MessageQueue_Post(channel->queue, messageCtx, 0, NULL, NULL);
|
||||
}
|
||||
|
||||
static void wts_queue_send_item(rdpPeerChannel* channel, BYTE* Buffer, UINT32 Length)
|
||||
|
@ -1027,28 +1037,35 @@ BOOL WINAPI FreeRDP_WTSVirtualChannelClose(HANDLE hChannelHandle)
|
|||
BOOL WINAPI FreeRDP_WTSVirtualChannelRead(HANDLE hChannelHandle, ULONG TimeOut, PCHAR Buffer, ULONG BufferSize, PULONG pBytesRead)
|
||||
{
|
||||
BYTE* buffer;
|
||||
UINT32 length;
|
||||
UINT16 channelId;
|
||||
wMessage message;
|
||||
wtsChannelMessage* messageCtx;
|
||||
rdpPeerChannel* channel = (rdpPeerChannel*) hChannelHandle;
|
||||
|
||||
if (!MessageQueue_Peek(channel->queue, &message, TRUE))
|
||||
if (!MessageQueue_Peek(channel->queue, &message, FALSE))
|
||||
{
|
||||
SetLastError(ERROR_NO_DATA);
|
||||
*pBytesRead = 0;
|
||||
return TRUE;
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
channelId = (UINT16) (UINT_PTR) message.context;
|
||||
buffer = (BYTE*) message.wParam;
|
||||
length = (UINT32) (UINT_PTR) message.lParam;
|
||||
messageCtx = (wtsChannelMessage*) (UINT_PTR) message.context;
|
||||
buffer = (BYTE*) (messageCtx + 1);
|
||||
|
||||
*pBytesRead = length;
|
||||
*pBytesRead = messageCtx->length - messageCtx->offset;
|
||||
if (Buffer == NULL || BufferSize == 0)
|
||||
{
|
||||
return TRUE;
|
||||
}
|
||||
if (*pBytesRead > BufferSize)
|
||||
*pBytesRead = BufferSize;
|
||||
|
||||
if (length > BufferSize)
|
||||
return FALSE;
|
||||
|
||||
CopyMemory(Buffer, buffer, length);
|
||||
free(buffer);
|
||||
CopyMemory(Buffer, buffer + messageCtx->offset, *pBytesRead);
|
||||
messageCtx->offset += *pBytesRead;
|
||||
if (messageCtx->offset >= messageCtx->length)
|
||||
{
|
||||
MessageQueue_Peek(channel->queue, &message, TRUE);
|
||||
free(messageCtx);
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
|
|
@ -936,6 +936,20 @@ static void update_send_bitmap_update(rdpContext* context, BITMAP_UPDATE* bitmap
|
|||
Stream_Release(s);
|
||||
}
|
||||
|
||||
static void update_send_play_sound(rdpContext* context, PLAY_SOUND_UPDATE* play_sound)
|
||||
{
|
||||
wStream* s;
|
||||
rdpRdp* rdp = context->rdp;
|
||||
|
||||
if (!rdp->settings->ReceivedCapabilities[CAPSET_TYPE_SOUND]) {
|
||||
return;
|
||||
}
|
||||
s = rdp_data_pdu_init(rdp);
|
||||
Stream_Write_UINT32(s, play_sound->duration);
|
||||
Stream_Write_UINT32(s, play_sound->frequency);
|
||||
rdp_send_data_pdu(rdp, s, DATA_PDU_TYPE_PLAY_SOUND, rdp->mcs->userId);
|
||||
Stream_Release(s);
|
||||
}
|
||||
/**
|
||||
* Primary Drawing Orders
|
||||
*/
|
||||
|
@ -1570,6 +1584,7 @@ void update_register_server_callbacks(rdpUpdate* update)
|
|||
update->SurfaceBits = update_send_surface_bits;
|
||||
update->SurfaceFrameMarker = update_send_surface_frame_marker;
|
||||
update->SurfaceCommand = update_send_surface_command;
|
||||
update->PlaySound = update_send_play_sound;
|
||||
update->primary->DstBlt = update_send_dstblt;
|
||||
update->primary->PatBlt = update_send_patblt;
|
||||
update->primary->ScrBlt = update_send_scrblt;
|
||||
|
|
|
@ -51,6 +51,7 @@ long bio_rdp_tls_callback(BIO* bio, int mode, const char* argp, int argi, long a
|
|||
|
||||
static int bio_rdp_tls_write(BIO* bio, const char* buf, int size)
|
||||
{
|
||||
int error;
|
||||
int status;
|
||||
BIO_RDP_TLS* tls = (BIO_RDP_TLS*) bio->ptr;
|
||||
|
||||
|
@ -70,11 +71,11 @@ static int bio_rdp_tls_write(BIO* bio, const char* buf, int size)
|
|||
break;
|
||||
|
||||
case SSL_ERROR_WANT_WRITE:
|
||||
BIO_set_flags(bio, BIO_FLAGS_WRITE);
|
||||
BIO_set_flags(bio, BIO_FLAGS_WRITE | BIO_FLAGS_SHOULD_RETRY);
|
||||
break;
|
||||
|
||||
case SSL_ERROR_WANT_READ:
|
||||
BIO_set_flags(bio, BIO_FLAGS_READ);
|
||||
BIO_set_flags(bio, BIO_FLAGS_READ | BIO_FLAGS_SHOULD_RETRY);
|
||||
break;
|
||||
|
||||
case SSL_ERROR_WANT_X509_LOOKUP:
|
||||
|
@ -88,7 +89,16 @@ static int bio_rdp_tls_write(BIO* bio, const char* buf, int size)
|
|||
break;
|
||||
|
||||
case SSL_ERROR_SYSCALL:
|
||||
error = WSAGetLastError();
|
||||
if ((error == WSAEWOULDBLOCK) || (error == WSAEINTR) ||
|
||||
(error == WSAEINPROGRESS) || (error == WSAEALREADY))
|
||||
{
|
||||
BIO_set_flags(bio, (BIO_FLAGS_WRITE | BIO_FLAGS_SHOULD_RETRY));
|
||||
}
|
||||
else
|
||||
{
|
||||
BIO_clear_flags(bio, BIO_FLAGS_SHOULD_RETRY);
|
||||
}
|
||||
break;
|
||||
|
||||
case SSL_ERROR_SSL:
|
||||
|
@ -102,6 +112,7 @@ static int bio_rdp_tls_write(BIO* bio, const char* buf, int size)
|
|||
|
||||
static int bio_rdp_tls_read(BIO* bio, char* buf, int size)
|
||||
{
|
||||
int error;
|
||||
int status;
|
||||
BIO_RDP_TLS* tls = (BIO_RDP_TLS*) bio->ptr;
|
||||
|
||||
|
@ -121,11 +132,11 @@ static int bio_rdp_tls_read(BIO* bio, char* buf, int size)
|
|||
break;
|
||||
|
||||
case SSL_ERROR_WANT_READ:
|
||||
BIO_set_flags(bio, BIO_FLAGS_READ);
|
||||
BIO_set_flags(bio, BIO_FLAGS_READ | BIO_FLAGS_SHOULD_RETRY);
|
||||
break;
|
||||
|
||||
case SSL_ERROR_WANT_WRITE:
|
||||
BIO_set_flags(bio, BIO_FLAGS_WRITE);
|
||||
BIO_set_flags(bio, BIO_FLAGS_WRITE | BIO_FLAGS_SHOULD_RETRY);
|
||||
break;
|
||||
|
||||
case SSL_ERROR_WANT_X509_LOOKUP:
|
||||
|
@ -152,8 +163,16 @@ static int bio_rdp_tls_read(BIO* bio, char* buf, int size)
|
|||
break;
|
||||
|
||||
case SSL_ERROR_SYSCALL:
|
||||
error = WSAGetLastError();
|
||||
if ((error == WSAEWOULDBLOCK) || (error == WSAEINTR) ||
|
||||
(error == WSAEINPROGRESS) || (error == WSAEALREADY))
|
||||
{
|
||||
BIO_set_flags(bio, (BIO_FLAGS_READ | BIO_FLAGS_SHOULD_RETRY));
|
||||
}
|
||||
else
|
||||
{
|
||||
BIO_clear_flags(bio, BIO_FLAGS_SHOULD_RETRY);
|
||||
status = -1;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -45,7 +45,7 @@ echo "Preparing OpenSSL..."
|
|||
OPENSSL_SRC=$ROOT/openssl-build
|
||||
if [ -d $OPENSSL_SRC ]; then
|
||||
cd $OPENSSL_SRC
|
||||
git pull
|
||||
git fetch
|
||||
RETVAL=$?
|
||||
else
|
||||
git clone $OPENSSL_SCM $OPENSSL_SRC
|
||||
|
@ -64,9 +64,7 @@ make clean
|
|||
# The makefile has a bug, which aborts during
|
||||
# first compilation. Rerun make to build the whole lib.
|
||||
make
|
||||
make
|
||||
make
|
||||
RETVAL=0 # TODO: Check, why 2 is returned.
|
||||
RETVAL=$?
|
||||
if [ $RETVAL -ne 0 ]; then
|
||||
echo "Failed to execute make command [$RETVAL]"
|
||||
exit -4
|
||||
|
|
|
@ -160,7 +160,7 @@ BOOL wf_peer_rdpsnd_init(wfPeerContext* context)
|
|||
|
||||
context->rdpsnd->Activated = wf_peer_rdpsnd_activated;
|
||||
|
||||
context->rdpsnd->Initialize(context->rdpsnd);
|
||||
context->rdpsnd->Initialize(context->rdpsnd, TRUE);
|
||||
|
||||
wf_rdpsnd_set_latest_peer(context);
|
||||
|
||||
|
|
|
@ -156,8 +156,16 @@ WINPR_API LONG InterlockedCompareExchange(LONG volatile *Destination, LONG Excha
|
|||
|
||||
#endif /* _WIN32 */
|
||||
|
||||
#if (!defined(_WIN32) || (defined(_WIN32) && (_WIN32_WINNT < 0x0502)))
|
||||
#define WINPR_INTERLOCKED_COMPARE_EXCHANGE64 1
|
||||
#endif
|
||||
|
||||
#ifdef WINPR_INTERLOCKED_COMPARE_EXCHANGE64
|
||||
|
||||
WINPR_API LONGLONG InterlockedCompareExchange64(LONGLONG volatile *Destination, LONGLONG Exchange, LONGLONG Comperand);
|
||||
|
||||
#endif
|
||||
|
||||
/* Doubly-Linked List */
|
||||
|
||||
WINPR_API VOID InitializeListHead(PLIST_ENTRY ListHead);
|
||||
|
|
|
@ -81,7 +81,6 @@ typedef struct _TP_CALLBACK_ENVIRON_V1
|
|||
|
||||
/* Non-Windows and pre Windows 7 */
|
||||
#if ((!defined(_WIN32)) || (defined(_WIN32) && (_WIN32_WINNT < 0x0601)))
|
||||
//#if !defined(_WIN32_WINNT_VISTA)
|
||||
|
||||
typedef struct _TP_CALLBACK_ENVIRON_V3
|
||||
{
|
||||
|
@ -121,7 +120,9 @@ typedef struct _TP_WAIT TP_WAIT, *PTP_WAIT;
|
|||
|
||||
typedef struct _TP_IO TP_IO, *PTP_IO;
|
||||
|
||||
#if (defined(_WIN32) && (_WIN32_WINNT < 0x0601))
|
||||
typedef TP_CALLBACK_ENVIRON_V1 TP_CALLBACK_ENVIRON, *PTP_CALLBACK_ENVIRON;
|
||||
#endif
|
||||
|
||||
#ifndef _WIN32
|
||||
|
||||
|
@ -152,13 +153,18 @@ typedef VOID (*PTP_WIN32_IO_CALLBACK)(PTP_CALLBACK_INSTANCE Instance, PVOID Cont
|
|||
|
||||
#endif
|
||||
|
||||
#if (!defined(_WIN32) || ((defined(_WIN32) && (_WIN32_WINNT < 0x0601))))
|
||||
#define WINPR_THREAD_POOL 1
|
||||
#endif
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
|
||||
/* Synch */
|
||||
|
||||
#ifdef WINPR_THREAD_POOL
|
||||
|
||||
WINPR_API PTP_WAIT CreateThreadpoolWait(PTP_WAIT_CALLBACK pfnwa, PVOID pv, PTP_CALLBACK_ENVIRON pcbe);
|
||||
WINPR_API VOID CloseThreadpoolWait(PTP_WAIT pwa);
|
||||
WINPR_API VOID SetThreadpoolWait(PTP_WAIT pwa, HANDLE h, PFILETIME pftTimeout);
|
||||
|
@ -225,6 +231,8 @@ WINPR_API VOID LeaveCriticalSectionWhenCallbackReturns(PTP_CALLBACK_INSTANCE pci
|
|||
WINPR_API VOID FreeLibraryWhenCallbackReturns(PTP_CALLBACK_INSTANCE pci, HMODULE mod);
|
||||
WINPR_API VOID DisassociateCurrentThreadFromCallback(PTP_CALLBACK_INSTANCE pci);
|
||||
|
||||
#endif
|
||||
|
||||
/* Dummy */
|
||||
|
||||
WINPR_API void winpr_pool_dummy(void);
|
||||
|
|
|
@ -297,7 +297,7 @@ WINPR_API BOOL DeleteTimerQueueTimer(HANDLE TimerQueue, HANDLE Timer, HANDLE Com
|
|||
|
||||
#endif
|
||||
|
||||
#if ((defined _WIN32) && (_WIN32_WINNT < 0x0403))
|
||||
#if (defined(_WIN32) && (_WIN32_WINNT < 0x0600))
|
||||
|
||||
WINPR_API BOOL InitializeCriticalSectionEx(LPCRITICAL_SECTION lpCriticalSection, DWORD dwSpinCount, DWORD Flags);
|
||||
|
||||
|
|
|
@ -33,6 +33,6 @@ set(${MODULE_PREFIX}_SRCS
|
|||
|
||||
winpr_module_add(${${MODULE_PREFIX}_SRCS})
|
||||
|
||||
if(BUILD_TESTING)
|
||||
if(BUILD_TESTING AND UNIX AND NOT WIN32)
|
||||
add_subdirectory(test)
|
||||
endif()
|
||||
|
|
|
@ -90,9 +90,10 @@ int TestGetCommState(int argc, char* argv[])
|
|||
return EXIT_FAILURE;
|
||||
}
|
||||
|
||||
hComm = CreateFile("COM1",
|
||||
hComm = CreateFileA("COM1",
|
||||
GENERIC_READ | GENERIC_WRITE,
|
||||
0, NULL, OPEN_EXISTING, 0, NULL);
|
||||
|
||||
if (hComm == INVALID_HANDLE_VALUE)
|
||||
{
|
||||
printf("CreateFileA failure: 0x%x\n", GetLastError());
|
||||
|
|
|
@ -19,7 +19,10 @@
|
|||
|
||||
#include <stdio.h>
|
||||
#include <sys/stat.h>
|
||||
|
||||
#ifndef _WIN32
|
||||
#include <termios.h>
|
||||
#endif
|
||||
|
||||
#include <winpr/comm.h>
|
||||
#include <winpr/crt.h>
|
||||
|
|
|
@ -19,7 +19,10 @@
|
|||
|
||||
#include <stdio.h>
|
||||
#include <sys/stat.h>
|
||||
|
||||
#ifndef _WIN32
|
||||
#include <termios.h>
|
||||
#endif
|
||||
|
||||
#include <winpr/comm.h>
|
||||
#include <winpr/crt.h>
|
||||
|
|
|
@ -19,7 +19,10 @@
|
|||
|
||||
#include <stdio.h>
|
||||
#include <sys/stat.h>
|
||||
|
||||
#ifndef _WIN32
|
||||
#include <termios.h>
|
||||
#endif
|
||||
|
||||
#include <winpr/comm.h>
|
||||
#include <winpr/crt.h>
|
||||
|
|
|
@ -20,6 +20,10 @@ winpr_module_add(
|
|||
crypto.h
|
||||
cert.c)
|
||||
|
||||
if(WIN32)
|
||||
winpr_library_add(crypt32)
|
||||
endif()
|
||||
|
||||
if(BUILD_TESTING)
|
||||
add_subdirectory(test)
|
||||
endif()
|
||||
|
|
|
@ -236,11 +236,11 @@ LONG InterlockedCompareExchange(LONG volatile *Destination, LONG Exchange, LONG
|
|||
|
||||
#endif /* _WIN32 */
|
||||
|
||||
#if defined(_WIN64)
|
||||
#if defined(_WIN32) && !defined(WINPR_INTERLOCKED_COMPARE_EXCHANGE64)
|
||||
|
||||
/* InterlockedCompareExchange64 already defined */
|
||||
|
||||
#elif (_WIN32 && (_WIN32_WINNT < 0x0502))
|
||||
#elif defined(_WIN32) && defined(WINPR_INTERLOCKED_COMPARE_EXCHANGE64)
|
||||
|
||||
static volatile HANDLE mutex = NULL;
|
||||
|
||||
|
@ -257,8 +257,6 @@ int static_mutex_lock(volatile HANDLE* static_mutex)
|
|||
return (WaitForSingleObject(*static_mutex, INFINITE) == WAIT_FAILED);
|
||||
}
|
||||
|
||||
/* Not available in XP */
|
||||
|
||||
LONGLONG InterlockedCompareExchange64(LONGLONG volatile *Destination, LONGLONG Exchange, LONGLONG Comperand)
|
||||
{
|
||||
LONGLONG previousValue = 0;
|
||||
|
|
|
@ -50,6 +50,8 @@ static void module_init()
|
|||
|
||||
#endif
|
||||
|
||||
#ifdef WINPR_THREAD_POOL
|
||||
|
||||
BOOL CallbackMayRunLong(PTP_CALLBACK_INSTANCE pci)
|
||||
{
|
||||
#ifdef _WIN32
|
||||
|
@ -61,3 +63,5 @@ BOOL CallbackMayRunLong(PTP_CALLBACK_INSTANCE pci)
|
|||
#endif
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
|
|
@ -62,6 +62,8 @@ static void module_init()
|
|||
|
||||
#endif
|
||||
|
||||
#ifdef WINPR_THREAD_POOL
|
||||
|
||||
VOID SetEventWhenCallbackReturns(PTP_CALLBACK_INSTANCE pci, HANDLE evt)
|
||||
{
|
||||
#ifdef _WIN32
|
||||
|
@ -128,5 +130,5 @@ VOID DisassociateCurrentThreadFromCallback(PTP_CALLBACK_INSTANCE pci)
|
|||
#endif
|
||||
}
|
||||
|
||||
|
||||
#endif
|
||||
|
||||
|
|
|
@ -26,6 +26,8 @@
|
|||
|
||||
#include "pool.h"
|
||||
|
||||
#ifdef WINPR_THREAD_POOL
|
||||
|
||||
VOID InitializeCallbackEnvironment_V1(TP_CALLBACK_ENVIRON_V1* pcbe)
|
||||
{
|
||||
pcbe->Version = 1;
|
||||
|
@ -55,6 +57,8 @@ VOID InitializeCallbackEnvironment_V3(TP_CALLBACK_ENVIRON_V3* pcbe)
|
|||
pcbe->Size = sizeof(TP_CALLBACK_ENVIRON);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#ifdef _WIN32
|
||||
|
||||
static BOOL module_initialized = FALSE;
|
||||
|
@ -116,6 +120,8 @@ PTP_CALLBACK_ENVIRON GetDefaultThreadpoolEnvironment()
|
|||
|
||||
#endif
|
||||
|
||||
#ifdef WINPR_THREAD_POOL
|
||||
|
||||
VOID InitializeThreadpoolEnvironment(PTP_CALLBACK_ENVIRON pcbe)
|
||||
{
|
||||
if (pcbe->Version == 3)
|
||||
|
@ -193,3 +199,5 @@ VOID SetThreadpoolCallbackPriority(PTP_CALLBACK_ENVIRON pcbe, TP_CALLBACK_PRIORI
|
|||
#else
|
||||
#endif
|
||||
}
|
||||
|
||||
#endif
|
||||
|
|
|
@ -56,6 +56,8 @@ static void module_init()
|
|||
|
||||
#endif
|
||||
|
||||
#if WINPR_THREAD_POOL
|
||||
|
||||
PTP_CLEANUP_GROUP CreateThreadpoolCleanupGroup()
|
||||
{
|
||||
PTP_CLEANUP_GROUP cleanupGroup = NULL;
|
||||
|
@ -94,4 +96,5 @@ VOID CloseThreadpoolCleanupGroup(PTP_CLEANUP_GROUP ptpcg)
|
|||
#endif
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
|
|
|
@ -24,6 +24,8 @@
|
|||
#include <winpr/crt.h>
|
||||
#include <winpr/pool.h>
|
||||
|
||||
#ifdef WINPR_THREAD_POOL
|
||||
|
||||
PTP_IO CreateThreadpoolIo(HANDLE fl, PTP_WIN32_IO_CALLBACK pfnio, PVOID pv, PTP_CALLBACK_ENVIRON pcbe)
|
||||
{
|
||||
return NULL;
|
||||
|
@ -49,3 +51,4 @@ VOID WaitForThreadpoolIoCallbacks(PTP_IO pio, BOOL fCancelPendingCallbacks)
|
|||
|
||||
}
|
||||
|
||||
#endif
|
|
@ -150,6 +150,8 @@ PTP_POOL GetDefaultThreadpool()
|
|||
|
||||
#endif
|
||||
|
||||
#ifdef WINPR_THREAD_POOL
|
||||
|
||||
PTP_POOL CreateThreadpool(PVOID reserved)
|
||||
{
|
||||
PTP_POOL pool = NULL;
|
||||
|
@ -236,6 +238,8 @@ VOID SetThreadpoolThreadMaximum(PTP_POOL ptpp, DWORD cthrdMost)
|
|||
#endif
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
/* dummy */
|
||||
|
||||
void winpr_pool_dummy()
|
||||
|
|
|
@ -24,6 +24,8 @@
|
|||
#include <winpr/crt.h>
|
||||
#include <winpr/pool.h>
|
||||
|
||||
#ifdef WINPR_THREAD_POOL
|
||||
|
||||
PTP_WAIT CreateThreadpoolWait(PTP_WAIT_CALLBACK pfnwa, PVOID pv, PTP_CALLBACK_ENVIRON pcbe)
|
||||
{
|
||||
return NULL;
|
||||
|
@ -44,4 +46,4 @@ VOID WaitForThreadpoolWaitCallbacks(PTP_WAIT pwa, BOOL fCancelPendingCallbacks)
|
|||
|
||||
}
|
||||
|
||||
|
||||
#endif
|
||||
|
|
|
@ -24,6 +24,8 @@
|
|||
#include <winpr/crt.h>
|
||||
#include <winpr/pool.h>
|
||||
|
||||
#ifdef WINPR_THREAD_POOL
|
||||
|
||||
PTP_TIMER CreateThreadpoolTimer(PTP_TIMER_CALLBACK pfnti, PVOID pv, PTP_CALLBACK_ENVIRON pcbe)
|
||||
{
|
||||
return NULL;
|
||||
|
@ -49,4 +51,4 @@ VOID WaitForThreadpoolTimerCallbacks(PTP_TIMER pti, BOOL fCancelPendingCallbacks
|
|||
|
||||
}
|
||||
|
||||
|
||||
#endif
|
|
@ -60,6 +60,8 @@ static void module_init()
|
|||
|
||||
#endif
|
||||
|
||||
#ifdef WINPR_THREAD_POOL
|
||||
|
||||
PTP_WORK CreateThreadpoolWork(PTP_WORK_CALLBACK pfnwk, PVOID pv, PTP_CALLBACK_ENVIRON pcbe)
|
||||
{
|
||||
PTP_WORK work = NULL;
|
||||
|
@ -153,3 +155,5 @@ VOID WaitForThreadpoolWorkCallbacks(PTP_WORK pwk, BOOL fCancelPendingCallbacks)
|
|||
printf("WaitForThreadpoolWorkCallbacks: error waiting on work completion\n");
|
||||
#endif
|
||||
}
|
||||
|
||||
#endif
|
||||
|
|
|
@ -235,7 +235,7 @@ VOID DeleteCriticalSection(LPCRITICAL_SECTION lpCriticalSection)
|
|||
|
||||
#endif
|
||||
|
||||
#if ((_WIN32) && (_WIN32_WINNT < 0x0403))
|
||||
#if (defined(_WIN32) && (_WIN32_WINNT < 0x0600))
|
||||
|
||||
typedef BOOL (WINAPI * PINITIALIZE_CRITICAL_SECTION_EX_FN)(LPCRITICAL_SECTION lpCriticalSection, DWORD dwSpinCount, DWORD Flags);
|
||||
|
||||
|
|
|
@ -27,8 +27,10 @@
|
|||
#include <winpr/cmdline.h>
|
||||
#include <winpr/sysinfo.h>
|
||||
|
||||
#include <openssl/pem.h>
|
||||
#include <openssl/conf.h>
|
||||
#include <openssl/pem.h>
|
||||
#include <openssl/err.h>
|
||||
#include <openssl/pkcs12.h>
|
||||
#include <openssl/x509v3.h>
|
||||
|
||||
#include <winpr/tools/makecert.h>
|
||||
|
@ -42,12 +44,24 @@ struct _MAKECERT_CONTEXT
|
|||
RSA* rsa;
|
||||
X509* x509;
|
||||
EVP_PKEY* pkey;
|
||||
PKCS12* pkcs12;
|
||||
|
||||
BOOL live;
|
||||
BOOL silent;
|
||||
|
||||
BOOL crtFormat;
|
||||
BOOL pemFormat;
|
||||
BOOL pfxFormat;
|
||||
|
||||
char* password;
|
||||
|
||||
char* output_file;
|
||||
char* output_path;
|
||||
char* default_name;
|
||||
char* common_name;
|
||||
|
||||
int duration_years;
|
||||
int duration_months;
|
||||
};
|
||||
|
||||
COMMAND_LINE_ARGUMENT_A args[] =
|
||||
|
@ -63,6 +77,15 @@ COMMAND_LINE_ARGUMENT_A args[] =
|
|||
{ "live", COMMAND_LINE_VALUE_FLAG, NULL, NULL, NULL, -1, NULL,
|
||||
"Generate certificate live in memory when used as a library."
|
||||
},
|
||||
{ "format", COMMAND_LINE_VALUE_REQUIRED, "<crt|pem|pfx>", NULL, NULL, -1, NULL,
|
||||
"Specify certificate file format"
|
||||
},
|
||||
{ "path", COMMAND_LINE_VALUE_REQUIRED, "<path>", NULL, NULL, -1, NULL,
|
||||
"Specify certificate file output path"
|
||||
},
|
||||
{ "p", COMMAND_LINE_VALUE_REQUIRED, "<password>", NULL, NULL, -1, NULL,
|
||||
"Specify certificate export password"
|
||||
},
|
||||
|
||||
/* Basic Options */
|
||||
|
||||
|
@ -154,6 +177,9 @@ COMMAND_LINE_ARGUMENT_A args[] =
|
|||
{ "m", COMMAND_LINE_VALUE_REQUIRED, "<number>", NULL, NULL, -1, NULL,
|
||||
"Specifies the duration, in months, of the certificate validity period."
|
||||
},
|
||||
{ "y", COMMAND_LINE_VALUE_REQUIRED, "<number>", NULL, NULL, -1, NULL,
|
||||
"Specifies the duration, in years, of the certificate validity period."
|
||||
},
|
||||
{ "nscp", COMMAND_LINE_VALUE_FLAG, NULL, NULL, NULL, -1, NULL,
|
||||
"Includes the Netscape client-authorization extension."
|
||||
},
|
||||
|
@ -346,6 +372,65 @@ int makecert_context_parse_arguments(MAKECERT_CONTEXT* context, int argc, char**
|
|||
{
|
||||
context->live = TRUE;
|
||||
}
|
||||
CommandLineSwitchCase(arg, "format")
|
||||
{
|
||||
if (!(arg->Flags & COMMAND_LINE_ARGUMENT_PRESENT))
|
||||
continue;
|
||||
|
||||
if (strcmp(arg->Value, "crt") == 0)
|
||||
{
|
||||
context->crtFormat = TRUE;
|
||||
context->pemFormat = FALSE;
|
||||
context->pfxFormat = FALSE;
|
||||
}
|
||||
else if (strcmp(arg->Value, "pem") == 0)
|
||||
{
|
||||
context->crtFormat = FALSE;
|
||||
context->pemFormat = TRUE;
|
||||
context->pfxFormat = FALSE;
|
||||
}
|
||||
else if (strcmp(arg->Value, "pfx") == 0)
|
||||
{
|
||||
context->crtFormat = FALSE;
|
||||
context->pemFormat = FALSE;
|
||||
context->pfxFormat = TRUE;
|
||||
}
|
||||
}
|
||||
CommandLineSwitchCase(arg, "path")
|
||||
{
|
||||
if (!(arg->Flags & COMMAND_LINE_ARGUMENT_PRESENT))
|
||||
continue;
|
||||
|
||||
context->output_path = _strdup(arg->Value);
|
||||
}
|
||||
CommandLineSwitchCase(arg, "p")
|
||||
{
|
||||
if (!(arg->Flags & COMMAND_LINE_ARGUMENT_PRESENT))
|
||||
continue;
|
||||
|
||||
context->password = _strdup(arg->Value);
|
||||
}
|
||||
CommandLineSwitchCase(arg, "n")
|
||||
{
|
||||
if (!(arg->Flags & COMMAND_LINE_ARGUMENT_PRESENT))
|
||||
continue;
|
||||
|
||||
context->common_name = _strdup(arg->Value);
|
||||
}
|
||||
CommandLineSwitchCase(arg, "y")
|
||||
{
|
||||
if (!(arg->Flags & COMMAND_LINE_ARGUMENT_PRESENT))
|
||||
continue;
|
||||
|
||||
context->duration_years = atoi(arg->Value);
|
||||
}
|
||||
CommandLineSwitchCase(arg, "m")
|
||||
{
|
||||
if (!(arg->Flags & COMMAND_LINE_ARGUMENT_PRESENT))
|
||||
continue;
|
||||
|
||||
context->duration_months = atoi(arg->Value);
|
||||
}
|
||||
|
||||
CommandLineSwitchDefault(arg)
|
||||
{
|
||||
|
@ -374,7 +459,7 @@ int makecert_context_output_certificate_file(MAKECERT_CONTEXT* context, char* pa
|
|||
char* fullpath;
|
||||
|
||||
if (!context->output_file)
|
||||
context->output_file = context->default_name;
|
||||
context->output_file = _strdup(context->default_name);
|
||||
|
||||
/*
|
||||
* Output Certificate File
|
||||
|
@ -383,7 +468,13 @@ int makecert_context_output_certificate_file(MAKECERT_CONTEXT* context, char* pa
|
|||
length = strlen(context->output_file);
|
||||
filename = malloc(length + 8);
|
||||
strcpy(filename, context->output_file);
|
||||
|
||||
if (context->crtFormat)
|
||||
strcpy(&filename[length], ".crt");
|
||||
else if (context->pemFormat)
|
||||
strcpy(&filename[length], ".pem");
|
||||
else if (context->pfxFormat)
|
||||
strcpy(&filename[length], ".pfx");
|
||||
|
||||
if (path)
|
||||
fullpath = GetCombinedPath(path, filename);
|
||||
|
@ -393,8 +484,32 @@ int makecert_context_output_certificate_file(MAKECERT_CONTEXT* context, char* pa
|
|||
fp = fopen(fullpath, "w+");
|
||||
|
||||
if (fp)
|
||||
{
|
||||
if (context->pfxFormat)
|
||||
{
|
||||
if (!context->password)
|
||||
{
|
||||
context->password = _strdup("password");
|
||||
printf("Using default export password \"password\"\n");
|
||||
}
|
||||
|
||||
OpenSSL_add_all_algorithms();
|
||||
OpenSSL_add_all_ciphers();
|
||||
OpenSSL_add_all_digests();
|
||||
|
||||
context->pkcs12 = PKCS12_create(context->password, context->default_name, context->pkey,
|
||||
context->x509, NULL, 0, 0, 0, 0, 0);
|
||||
|
||||
i2d_PKCS12_fp(fp, context->pkcs12);
|
||||
}
|
||||
else
|
||||
{
|
||||
PEM_write_X509(fp, context->x509);
|
||||
|
||||
if (context->pemFormat)
|
||||
PEM_write_PrivateKey(fp, context->pkey, NULL, NULL, 0, NULL, NULL);
|
||||
}
|
||||
|
||||
fclose(fp);
|
||||
}
|
||||
|
||||
|
@ -411,6 +526,9 @@ int makecert_context_output_private_key_file(MAKECERT_CONTEXT* context, char* pa
|
|||
char* filename;
|
||||
char* fullpath;
|
||||
|
||||
if (!context->crtFormat)
|
||||
return 1;
|
||||
|
||||
if (!context->output_file)
|
||||
context->output_file = context->default_name;
|
||||
|
||||
|
@ -456,7 +574,13 @@ int makecert_context_process(MAKECERT_CONTEXT* context, int argc, char** argv)
|
|||
if (makecert_context_parse_arguments(context, argc, argv) < 1)
|
||||
return 0;
|
||||
|
||||
if (!context->default_name && !context->common_name)
|
||||
context->default_name = x509_get_default_name();
|
||||
else
|
||||
context->default_name = _strdup(context->common_name);
|
||||
|
||||
if (!context->common_name)
|
||||
context->common_name = _strdup(context->default_name);
|
||||
|
||||
CRYPTO_mem_ctrl(CRYPTO_MEM_CHECK_ON);
|
||||
context->bio = BIO_new_fp(stderr, BIO_NOCLOSE);
|
||||
|
@ -501,7 +625,16 @@ int makecert_context_process(MAKECERT_CONTEXT* context, int argc, char** argv)
|
|||
ASN1_INTEGER_set(X509_get_serialNumber(context->x509), serial);
|
||||
|
||||
X509_gmtime_adj(X509_get_notBefore(context->x509), 0);
|
||||
X509_gmtime_adj(X509_get_notAfter(context->x509), (long) 60 * 60 * 24 * 365);
|
||||
|
||||
if (context->duration_months)
|
||||
{
|
||||
X509_gmtime_adj(X509_get_notAfter(context->x509), (long) (60 * 60 * 24 * 31 * context->duration_months));
|
||||
}
|
||||
else if (context->duration_years)
|
||||
{
|
||||
X509_gmtime_adj(X509_get_notAfter(context->x509), (long) (60 * 60 * 24 * 365 * context->duration_years));
|
||||
}
|
||||
|
||||
X509_set_pubkey(context->x509, context->pkey);
|
||||
|
||||
name = X509_get_subject_name(context->x509);
|
||||
|
@ -535,19 +668,14 @@ int makecert_context_process(MAKECERT_CONTEXT* context, int argc, char** argv)
|
|||
if (entry)
|
||||
X509_NAME_add_entry_by_txt(name, "OU", MBSTRING_UTF8, (const unsigned char*) entry, length, -1, 0);
|
||||
|
||||
entry = x509_name_parse(arg->Value, "CN", &length);
|
||||
|
||||
if (!entry)
|
||||
{
|
||||
entry = context->default_name;
|
||||
entry = context->common_name;
|
||||
length = strlen(entry);
|
||||
}
|
||||
|
||||
X509_NAME_add_entry_by_txt(name, "CN", MBSTRING_UTF8, (const unsigned char*) entry, length, -1, 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
entry = context->default_name;
|
||||
entry = context->common_name;
|
||||
length = strlen(entry);
|
||||
|
||||
X509_NAME_add_entry_by_txt(name, "CN", MBSTRING_UTF8, (const unsigned char*) entry, length, -1, 0);
|
||||
|
@ -592,8 +720,10 @@ int makecert_context_process(MAKECERT_CONTEXT* context, int argc, char** argv)
|
|||
|
||||
if (!context->live)
|
||||
{
|
||||
makecert_context_output_certificate_file(context, NULL);
|
||||
makecert_context_output_private_key_file(context, NULL);
|
||||
makecert_context_output_certificate_file(context, context->output_path);
|
||||
|
||||
if (context->crtFormat)
|
||||
makecert_context_output_private_key_file(context, context->output_path);
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
@ -603,11 +733,12 @@ MAKECERT_CONTEXT* makecert_context_new()
|
|||
{
|
||||
MAKECERT_CONTEXT* context = NULL;
|
||||
|
||||
context = (MAKECERT_CONTEXT*) malloc(sizeof(MAKECERT_CONTEXT));
|
||||
context = (MAKECERT_CONTEXT*) calloc(1, sizeof(MAKECERT_CONTEXT));
|
||||
|
||||
if (context)
|
||||
{
|
||||
ZeroMemory(context, sizeof(MAKECERT_CONTEXT));
|
||||
context->crtFormat = TRUE;
|
||||
context->duration_years = 1;
|
||||
}
|
||||
|
||||
return context;
|
||||
|
@ -617,6 +748,8 @@ void makecert_context_free(MAKECERT_CONTEXT* context)
|
|||
{
|
||||
if (context)
|
||||
{
|
||||
free(context->password);
|
||||
|
||||
X509_free(context->x509);
|
||||
EVP_PKEY_free(context->pkey);
|
||||
|
||||
|
|
Loading…
Reference in New Issue