Add iOS proxy source code

This commit is contained in:
Dennis Heinze
2019-06-07 00:38:55 +02:00
parent 3b1222e327
commit 1a2e4e90ca
7 changed files with 692 additions and 0 deletions
+3
View File
@@ -14,3 +14,6 @@ _internalblue.hist
_internalblue.log
btsnoop.log
# xcode
xcuserdata
*.xcworkspace
+20
View File
@@ -0,0 +1,20 @@
# internalblue-ios-proxy
This project is a proxy that redirects iOS's bluetooth socket and exposes it as a TCP socket which can be used to send HCI commands to the bluetooth controller of the device. A jailbroken device is required. To compile the project, a Mac with xcode is required.
## Building internalblue-ios-proxy
Open the project with xcode and compile it. Xcode will create a single binary that can then be transferred onto the device.
## Installing internalblue-ios-proxy
1. Right-click the `internalblue-ios-proxy` binary and click "Show in Finder". This will open the location the compiled binary resides in.
2. Move the binary onto the device (e.g. with scp) at a location where applications are allowed to be executed (e.g. `/bin` or `/sbin`).
3. The binary needs the `platform-binary` entitlement. This is achieved by signing the binary with the included `entitlements.xml` file. Sign it using `ldid -Sentitlements.xml internalblue-ios-proxy`. `ldid` should be on a jailbroken device with Cydia by default.
## Running internalblue-ios-proxy
Run the proxy by executing `internalblue-ios-proxy <port-number>`. The phone will then listen on this port and can be accessed either when on the same WiFi or by proxying the port through USB (using [usbmuxd](https://iphonedevwiki.net/index.php/SSH_Over_USB)).
A few things to note:
- to increase reliability of the proxy, bluetooth should be disabled (either by manually stopping the bluetoothd daemon or by shutting of bluetooth in the settings on the phone)
- in case the bluetooth chip crashes or does not respond anymore over the proxy, the proxy should be stopped and bluetooth should be turned off and on again in the UI
- sometimes the bluetooth socket will not respond anymore after establishing a second connection, just restart the proxy then.
This project is based on Brandon Azad's [iOS command line tool](https://github.com/bazad/ios-command-line-tool) template.
+8
View File
@@ -0,0 +1,8 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>platform-application</key>
<true/>
</dict>
</plist>
@@ -0,0 +1,285 @@
// !$*UTF8*$!
{
archiveVersion = 1;
classes = {
};
objectVersion = 50;
objects = {
/* Begin PBXBuildFile section */
BB958F25227BA4580029C2D6 /* internalblue-ios-proxy.c in Sources */ = {isa = PBXBuildFile; fileRef = BB958F24227BA4580029C2D6 /* internalblue-ios-proxy.c */; };
/* End PBXBuildFile section */
/* Begin PBXFileReference section */
551A88C4208E671F0048DFA0 /* internalblue-ios-proxy */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.dylib"; includeInIndex = 0; path = "internalblue-ios-proxy"; sourceTree = BUILT_PRODUCTS_DIR; };
BB958F23227BA4580029C2D6 /* internalblue-ios-proxy.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "internalblue-ios-proxy.h"; sourceTree = "<group>"; };
BB958F24227BA4580029C2D6 /* internalblue-ios-proxy.c */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.c; path = "internalblue-ios-proxy.c"; sourceTree = "<group>"; };
/* End PBXFileReference section */
/* Begin PBXFrameworksBuildPhase section */
551A88C1208E671F0048DFA0 /* Frameworks */ = {
isa = PBXFrameworksBuildPhase;
buildActionMask = 2147483647;
files = (
);
runOnlyForDeploymentPostprocessing = 0;
};
/* End PBXFrameworksBuildPhase section */
/* Begin PBXGroup section */
551A88BB208E671F0048DFA0 = {
isa = PBXGroup;
children = (
551A88C6208E671F0048DFA0 /* internalblue-ios-proxy */,
551A88C5208E671F0048DFA0 /* Products */,
);
sourceTree = "<group>";
};
551A88C5208E671F0048DFA0 /* Products */ = {
isa = PBXGroup;
children = (
551A88C4208E671F0048DFA0 /* internalblue-ios-proxy */,
);
name = Products;
sourceTree = "<group>";
};
551A88C6208E671F0048DFA0 /* internalblue-ios-proxy */ = {
isa = PBXGroup;
children = (
BB958F23227BA4580029C2D6 /* internalblue-ios-proxy.h */,
BB958F24227BA4580029C2D6 /* internalblue-ios-proxy.c */,
);
path = "internalblue-ios-proxy";
sourceTree = "<group>";
};
/* End PBXGroup section */
/* Begin PBXNativeTarget section */
551A88C3208E671F0048DFA0 /* internalblue-ios-proxy */ = {
isa = PBXNativeTarget;
buildConfigurationList = 551A88CD208E671F0048DFA0 /* Build configuration list for PBXNativeTarget "internalblue-ios-proxy" */;
buildPhases = (
551A88C0208E671F0048DFA0 /* Sources */,
551A88C1208E671F0048DFA0 /* Frameworks */,
);
buildRules = (
);
dependencies = (
);
name = "internalblue-ios-proxy";
productName = "ios-command-line-tool";
productReference = 551A88C4208E671F0048DFA0 /* internalblue-ios-proxy */;
productType = "com.apple.product-type.library.dynamic";
};
/* End PBXNativeTarget section */
/* Begin PBXProject section */
551A88BC208E671F0048DFA0 /* Project object */ = {
isa = PBXProject;
attributes = {
LastUpgradeCheck = 0930;
ORGANIZATIONNAME = ttdennis;
TargetAttributes = {
551A88C3208E671F0048DFA0 = {
CreatedOnToolsVersion = 9.3;
};
};
};
buildConfigurationList = 551A88BF208E671F0048DFA0 /* Build configuration list for PBXProject "internalblue-ios-proxy" */;
compatibilityVersion = "Xcode 9.3";
developmentRegion = en;
hasScannedForEncodings = 0;
knownRegions = (
en,
);
mainGroup = 551A88BB208E671F0048DFA0;
productRefGroup = 551A88C5208E671F0048DFA0 /* Products */;
projectDirPath = "";
projectRoot = "";
targets = (
551A88C3208E671F0048DFA0 /* internalblue-ios-proxy */,
);
};
/* End PBXProject section */
/* Begin PBXSourcesBuildPhase section */
551A88C0208E671F0048DFA0 /* Sources */ = {
isa = PBXSourcesBuildPhase;
buildActionMask = 2147483647;
files = (
BB958F25227BA4580029C2D6 /* internalblue-ios-proxy.c in Sources */,
);
runOnlyForDeploymentPostprocessing = 0;
};
/* End PBXSourcesBuildPhase section */
/* Begin XCBuildConfiguration section */
551A88CB208E671F0048DFA0 /* Debug */ = {
isa = XCBuildConfiguration;
buildSettings = {
ALWAYS_SEARCH_USER_PATHS = NO;
CLANG_ANALYZER_NONNULL = YES;
CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE;
CLANG_CXX_LANGUAGE_STANDARD = "gnu++14";
CLANG_CXX_LIBRARY = "libc++";
CLANG_ENABLE_MODULES = YES;
CLANG_ENABLE_OBJC_ARC = YES;
CLANG_ENABLE_OBJC_WEAK = YES;
CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
CLANG_WARN_BOOL_CONVERSION = YES;
CLANG_WARN_COMMA = YES;
CLANG_WARN_CONSTANT_CONVERSION = YES;
CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
CLANG_WARN_DOCUMENTATION_COMMENTS = YES;
CLANG_WARN_EMPTY_BODY = YES;
CLANG_WARN_ENUM_CONVERSION = YES;
CLANG_WARN_INFINITE_RECURSION = YES;
CLANG_WARN_INT_CONVERSION = YES;
CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
CLANG_WARN_STRICT_PROTOTYPES = YES;
CLANG_WARN_SUSPICIOUS_MOVE = YES;
CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE;
CLANG_WARN_UNREACHABLE_CODE = YES;
CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
CODE_SIGN_IDENTITY = "iPhone Developer";
COPY_PHASE_STRIP = NO;
DEBUG_INFORMATION_FORMAT = dwarf;
ENABLE_STRICT_OBJC_MSGSEND = YES;
ENABLE_TESTABILITY = YES;
GCC_C_LANGUAGE_STANDARD = gnu11;
GCC_DYNAMIC_NO_PIC = NO;
GCC_NO_COMMON_BLOCKS = YES;
GCC_OPTIMIZATION_LEVEL = 0;
GCC_PREPROCESSOR_DEFINITIONS = (
"DEBUG=1",
"$(inherited)",
);
GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
GCC_WARN_UNDECLARED_SELECTOR = YES;
GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
GCC_WARN_UNUSED_FUNCTION = YES;
GCC_WARN_UNUSED_VARIABLE = YES;
IPHONEOS_DEPLOYMENT_TARGET = 11.0;
MTL_ENABLE_DEBUG_INFO = YES;
ONLY_ACTIVE_ARCH = YES;
SDKROOT = iphoneos;
};
name = Debug;
};
551A88CC208E671F0048DFA0 /* Release */ = {
isa = XCBuildConfiguration;
buildSettings = {
ALWAYS_SEARCH_USER_PATHS = NO;
CLANG_ANALYZER_NONNULL = YES;
CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE;
CLANG_CXX_LANGUAGE_STANDARD = "gnu++14";
CLANG_CXX_LIBRARY = "libc++";
CLANG_ENABLE_MODULES = YES;
CLANG_ENABLE_OBJC_ARC = YES;
CLANG_ENABLE_OBJC_WEAK = YES;
CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
CLANG_WARN_BOOL_CONVERSION = YES;
CLANG_WARN_COMMA = YES;
CLANG_WARN_CONSTANT_CONVERSION = YES;
CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
CLANG_WARN_DOCUMENTATION_COMMENTS = YES;
CLANG_WARN_EMPTY_BODY = YES;
CLANG_WARN_ENUM_CONVERSION = YES;
CLANG_WARN_INFINITE_RECURSION = YES;
CLANG_WARN_INT_CONVERSION = YES;
CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
CLANG_WARN_STRICT_PROTOTYPES = YES;
CLANG_WARN_SUSPICIOUS_MOVE = YES;
CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE;
CLANG_WARN_UNREACHABLE_CODE = YES;
CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
CODE_SIGN_IDENTITY = "iPhone Developer";
COPY_PHASE_STRIP = NO;
DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym";
ENABLE_NS_ASSERTIONS = NO;
ENABLE_STRICT_OBJC_MSGSEND = YES;
GCC_C_LANGUAGE_STANDARD = gnu11;
GCC_NO_COMMON_BLOCKS = YES;
GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
GCC_WARN_UNDECLARED_SELECTOR = YES;
GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
GCC_WARN_UNUSED_FUNCTION = YES;
GCC_WARN_UNUSED_VARIABLE = YES;
IPHONEOS_DEPLOYMENT_TARGET = 11.0;
MTL_ENABLE_DEBUG_INFO = NO;
SDKROOT = iphoneos;
VALIDATE_PRODUCT = YES;
};
name = Release;
};
551A88CE208E671F0048DFA0 /* Debug */ = {
isa = XCBuildConfiguration;
buildSettings = {
CODE_SIGN_STYLE = Automatic;
DEVELOPMENT_TEAM = RSU3RMH9UZ;
DYLIB_COMPATIBILITY_VERSION = "";
DYLIB_CURRENT_VERSION = "";
EXECUTABLE_PREFIX = "";
EXECUTABLE_SUFFIX = "";
MACH_O_TYPE = mh_execute;
OTHER_LDFLAGS = "-ObjC";
PRODUCT_NAME = "$(TARGET_NAME)";
SKIP_INSTALL = YES;
TARGETED_DEVICE_FAMILY = "1,2";
};
name = Debug;
};
551A88CF208E671F0048DFA0 /* Release */ = {
isa = XCBuildConfiguration;
buildSettings = {
CODE_SIGN_STYLE = Automatic;
DEVELOPMENT_TEAM = RSU3RMH9UZ;
DYLIB_COMPATIBILITY_VERSION = "";
DYLIB_CURRENT_VERSION = "";
EXECUTABLE_PREFIX = "";
EXECUTABLE_SUFFIX = "";
MACH_O_TYPE = mh_execute;
OTHER_LDFLAGS = "-ObjC";
PRODUCT_NAME = "$(TARGET_NAME)";
SKIP_INSTALL = YES;
TARGETED_DEVICE_FAMILY = "1,2";
};
name = Release;
};
/* End XCBuildConfiguration section */
/* Begin XCConfigurationList section */
551A88BF208E671F0048DFA0 /* Build configuration list for PBXProject "internalblue-ios-proxy" */ = {
isa = XCConfigurationList;
buildConfigurations = (
551A88CB208E671F0048DFA0 /* Debug */,
551A88CC208E671F0048DFA0 /* Release */,
);
defaultConfigurationIsVisible = 0;
defaultConfigurationName = Release;
};
551A88CD208E671F0048DFA0 /* Build configuration list for PBXNativeTarget "internalblue-ios-proxy" */ = {
isa = XCConfigurationList;
buildConfigurations = (
551A88CE208E671F0048DFA0 /* Debug */,
551A88CF208E671F0048DFA0 /* Release */,
);
defaultConfigurationIsVisible = 0;
defaultConfigurationName = Release;
};
/* End XCConfigurationList section */
};
rootObject = 551A88BC208E671F0048DFA0 /* Project object */;
}
@@ -0,0 +1,80 @@
<?xml version="1.0" encoding="UTF-8"?>
<Scheme
LastUpgradeVersion = "1020"
version = "1.3">
<BuildAction
parallelizeBuildables = "YES"
buildImplicitDependencies = "YES">
<BuildActionEntries>
<BuildActionEntry
buildForTesting = "YES"
buildForRunning = "YES"
buildForProfiling = "YES"
buildForArchiving = "YES"
buildForAnalyzing = "YES">
<BuildableReference
BuildableIdentifier = "primary"
BlueprintIdentifier = "551A88C3208E671F0048DFA0"
BuildableName = "internalblue-ios-proxy"
BlueprintName = "internalblue-ios-proxy"
ReferencedContainer = "container:internalblue-ios-proxy.xcodeproj">
</BuildableReference>
</BuildActionEntry>
</BuildActionEntries>
</BuildAction>
<TestAction
buildConfiguration = "Debug"
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
shouldUseLaunchSchemeArgsEnv = "YES">
<Testables>
</Testables>
<AdditionalOptions>
</AdditionalOptions>
</TestAction>
<LaunchAction
buildConfiguration = "Debug"
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
launchStyle = "0"
useCustomWorkingDirectory = "NO"
ignoresPersistentStateOnLaunch = "NO"
debugDocumentVersioning = "YES"
debugServiceExtension = "internal"
allowLocationSimulation = "YES">
<MacroExpansion>
<BuildableReference
BuildableIdentifier = "primary"
BlueprintIdentifier = "551A88C3208E671F0048DFA0"
BuildableName = "internalblue-ios-proxy"
BlueprintName = "internalblue-ios-proxy"
ReferencedContainer = "container:internalblue-ios-proxy.xcodeproj">
</BuildableReference>
</MacroExpansion>
<AdditionalOptions>
</AdditionalOptions>
</LaunchAction>
<ProfileAction
buildConfiguration = "Release"
shouldUseLaunchSchemeArgsEnv = "YES"
savedToolIdentifier = ""
useCustomWorkingDirectory = "NO"
debugDocumentVersioning = "YES">
<MacroExpansion>
<BuildableReference
BuildableIdentifier = "primary"
BlueprintIdentifier = "551A88C3208E671F0048DFA0"
BuildableName = "internalblue-ios-proxy"
BlueprintName = "internalblue-ios-proxy"
ReferencedContainer = "container:internalblue-ios-proxy.xcodeproj">
</BuildableReference>
</MacroExpansion>
</ProfileAction>
<AnalyzeAction
buildConfiguration = "Debug">
</AnalyzeAction>
<ArchiveAction
buildConfiguration = "Release"
revealArchiveInOrganizer = "YES">
</ArchiveAction>
</Scheme>
@@ -0,0 +1,282 @@
//
// internalblue-ios-proxy.c
// internalblue-ios-proxy
//
// Created by ttdennis on 03.05.19.
// Copyright © 2019 ttdennis. All rights reserved.
//
#include "internalblue-ios-proxy.h"
#include <stdlib.h>
#include <fcntl.h>
#include <string.h>
#include <sys/socket.h>
#include <sys/ioctl.h>
#include <sys/errno.h>
#include <sys/select.h>
#include <sys/time.h>
#include <arpa/inet.h>
#include <netinet/in.h>
#include <unistd.h>
#include <termios.h>
#define IOAOSSKYSETCHANNELSPEC 0x800C5414
#define IOAOSSKYGETCHANNELUUID 0x40105412
#define CTLIOCGINFO 0xC0644E03
typedef struct ctl_info {
uint32_t ctl_id;
char ctl_name[96];
} ctl_info_t;
int btwake_fd, bt_fd;
/*
This code has been put together by reverse-engineering BlueTool and bluetoothd on
iOS. Some of the things that happen here are not completely understood but the goal
was to just get it to work.
*/
int connect_bt_device() {
int socket_fd = socket(32, 1, 2);
int error = 0;
int ret = 0;
struct sockaddr sock_addr;
struct termios term;
if (socket_fd == 0) {
printf("unable to get bluetooth socket\n");
return -1;
}
ctl_info_t *ctl_inf = malloc(sizeof(ctl_info_t));
ctl_inf->ctl_id = 0;
strcpy(ctl_inf->ctl_name, "com.apple.uart.bluetooth");
if ((error = ioctl(socket_fd, CTLIOCGINFO, ctl_inf))) {
printf("ioctl(CTLIOCGINFO) = %d - errno: %d\n", error, errno);
printf("error: %s\n", strerror(errno));
return -1;
}
*(int *)&sock_addr.sa_len = 0x22020;
*(int *)&sock_addr.sa_data[2] = ctl_inf->ctl_id;
ret = connect(socket_fd, &sock_addr, 0x20);
if (ret != 0) {
printf("connect() = %d - errno: %d\n", ret, errno);
printf("error: %s\n", strerror(errno));
return -1;
}
printf("Connected to bt device\n");
socklen_t len = 72;
ret = getsockopt(socket_fd, 2, TIOCGETA, &term, &len);
if (ret != 0) {
printf("getsockopt(TIOCGETA) = %d - errno: %d\n", ret, errno);
printf("error: %s\n", strerror(errno));
return -1;
}
cfmakeraw(&term);
ret = cfsetspeed(&term, 3000000);
if (ret != 0) {
printf("cfsetspeed() = %d - errno: %d\n", ret, errno);
printf("error: %s\n", strerror(errno));
return -1;
}
term.c_iflag |= 4;
term.c_cflag = 232192;
ret = setsockopt(socket_fd, 2, TIOCSETA, &term, 0x48);
if (ret != 0) {
printf("setsockopt() = %d - errno: %d\n", ret, errno);
printf("error: %s\n", strerror(errno));
return -1;
}
tcflush(socket_fd, 3);
free(ctl_inf);
return socket_fd;
}
int create_server(int port) {
int server_fd;
struct sockaddr_in server;
int on = 1;
int addrlen;
server_fd = socket(AF_INET, SOCK_STREAM, 0);
if (server_fd < 0) {
printf("Unable to create server socket\n");
return -1;
}
addrlen = sizeof(server);
memset(&server, '\0', addrlen);
server.sin_family = AF_INET;
server.sin_addr.s_addr = INADDR_ANY;
server.sin_port = htons(port);
setsockopt(server_fd, SOL_SOCKET, SO_REUSEADDR, &on, 4);
if (bind(server_fd, (struct sockaddr *)&server, sizeof(server)) < 0) {
printf("Error binding socket\n");
return -1;
}
if (listen(server_fd, 5) < 0) {
printf("Failed listening: %s\n", strerror(errno));
return -1;
}
printf("Listening on port %d\n", port);
return server_fd;
}
int wait_for_connection(int server_fd) {
int client_fd;
socklen_t len;
struct sockaddr_in client;
len = sizeof(struct sockaddr_in);
client_fd = accept(server_fd, (struct sockaddr *)&client, (socklen_t *)&len);
if (client_fd < 0) {
printf("Accepting connection failed\n");
return -1;
}
return client_fd;
}
size_t buffered_write(int fd, char *buf, int *len)
{
size_t x = write(fd, buf, *len);
if (x < 0)
return x;
if (x == 0)
return x;
if (x != *len)
memmove(buf, buf+x, (*len)-x);
*len -= x;
return x;
}
void proxy_bt_socket(int client, int bt) {
char *client_buf, *bt_buf;
int nfds;
fd_set R;
int client_out = 0;
int bt_out = 0;
int x;
size_t n;
client_buf = malloc(1024);
bt_buf = malloc(1024);
nfds = client > bt ? client : bt;
nfds++;
while(1) {
struct timeval to;
if (client_out) {
buffered_write(bt, client_buf, &client_out);
}
if (bt_out) {
buffered_write(client, bt_buf, &bt_out);
}
FD_ZERO(&R);
if (client_out < 1024)
FD_SET(client, &R);
if (bt_out < 1024)
FD_SET(bt, &R);
to.tv_sec = 0;
to.tv_usec = 1000;
x = select(nfds+1, &R, 0, 0, &to);
if (x > 0) {
if (FD_ISSET(client, &R)) {
n = read(client, client_buf+client_out, 1024-client_out);
if (n > 0) {
client_out += n;
} else {
close(client);
printf("Client read failed\n");
return;
}
}
if (FD_ISSET(bt, &R)) {
n = read(bt, bt_buf+bt_out, 1024-bt_out);
if (n > 0) {
bt_out += n;
} else {
close(client);
printf("BT read failed\n");
return;
}
}
} else if (x < 0 && errno != EINTR){
printf("Select failed with %s\n", strerror(errno));
close(client);
return;
}
}
}
void __exit(int sig) {
close(bt_fd);
close(btwake_fd);
exit(0);
}
int main(int argc, char **argv) {
int server_fd, client_fd;
int port;
if (argc != 2) {
printf("Usage: %s <port_number>\n", argv[0]);
return 1;
}
port = atoi(argv[1]);
// wake BT device
btwake_fd = open("/dev/btwake", 0);
bt_fd = connect_bt_device();
if (bt_fd < 0) {
printf("Error connecting to bluetooth device\n");
return -1;
}
server_fd = create_server(port);
if (server_fd < 0) {
printf("Unable to create server\n");
return -1;
}
printf("Created server\n");
signal(SIGINT, __exit);
while (1) {
printf("Waiting for connection\n");
client_fd = wait_for_connection(server_fd);
if (client_fd < 0)
continue;
// currently only one connection is supported
proxy_bt_socket(client_fd, bt_fd);
close(client_fd);
}
return 0;
}
@@ -0,0 +1,14 @@
//
// internalblue-ios-proxy.h
// internalblue-ios-proxy
//
// Created by ttdennis on 03.05.19.
// Copyright © 2019 ttdennis. All rights reserved.
//
#ifndef internalblue_ios_proxy_h
#define internalblue_ios_proxy_h
#include <stdio.h>
#endif /* internalblue_ios_proxy_h */