-
Notifications
You must be signed in to change notification settings - Fork 3
/
Copy pathtungsten.c
208 lines (189 loc) · 7.34 KB
/
tungsten.c
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
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
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
/* File: tungsten.c
* Creation Date: December 17th, 2009
* Last Modified Date: January 9th, 2010
* Version: 0.1.14
* Contact: Adam Lamers <adam@millenniumsoftworks.com>
*/
/********************************************************************************
* This file is part of Tungsten. *
* *
* Tungsten is free software: you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation, either version 3 of the License, or *
* (at your option) any later version. *
* *
* Tungsten is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with Tungsten. If not, see <http://www.gnu.org/licenses/>. *
********************************************************************************/
#include "tungsten.h"
#include <stdio.h>
#include <windows.h>
char iPhone_LastError[255];
/** Retrieves the error string of the last error that occured in the library
* @return char* containing the error text.
*/
char *iPhone_GetLastError()
{
return iPhone_LastError;
}
/** Internal function: Set the error text of the last error that occured. */
void iPhone_SetLastError(char *format, ...)
{
va_list args;
va_start(args, format);
vsprintf(iPhone_LastError, format, args);
va_end(args);
}
/** Initializes an iPhone, registering it's callbacks to recieve device notifications.
* @param iphone Pointer to an iPhone struct with the dnc member is initialized to a DeviceNotification callback.
*/
void iPhone_init(iPhone *iphone)
{
void* notification = malloc(sizeof(void*));
int ret = AMDeviceNotificationSubscribe(iphone->dnc, 0, 0, 0, notification);
if(ret != 0)
iPhone_SetLastError("AMDeviceNotificationSubscribe failed with error %d", ret);
/*
ret = AMRestoreRegisterForDeviceNotifications(iphone->drn1, iphone->drn2, iphone->drn3, iphone->drn4, 0, NULL);
if(ret != 0)
iPhone_SetLastError("AMRestoreRegisterForDeviceNotifications failed with error %d", ret);
*/ /* Can't really do anything in recovery mode anyway. */
free(notification);
}
/** Determines whether or not a file exists on the device.
* @param iphone The iPhone on which to locate the file.
* @param path The UNIX style path to the file on the device.
* @return BOOL indicating whether or not the file exists. (TRUE = exists)
*/
BOOL iPhone_FileExists(iPhone *iphone, char *path)
{
void *data = NULL;
int ret = AFCFileInfoOpen(iphone->hAFC, path, &data);
if(ret == 0)
{
AFCKeyValueClose(data);
return TRUE;
}
else
return FALSE;
}
/** Debug function, retrieves all files in a directory and prints them to stdout */
BOOL GetFiles(iPhone* iphone, char *path)
{
if(iphone->connected == FALSE){ iPhone_SetLastError("GetFiles() failed, device not connected."); return FALSE; } //If we aren't connected, we can't get files.
void *hDir = NULL;
if(AFCDirectoryOpen(iphone->hAFC, path, &hDir) != 0){ iPhone_SetLastError("AFCDirectoryOpen failed"); return FALSE; }
char *buffer = NULL;
while(1)
{
AFCDirectoryRead(iphone->hAFC, hDir, &buffer);
if(buffer == NULL) break;
printf("%s\n", buffer);
}
AFCDirectoryClose(iphone->hAFC, hDir);
return TRUE;
}
/** Connect to an iPhone device, and register callbacks.
* Members of the iPhone struct that must be valid: dnc
* for device notifications
*/
BOOL iPhone_Connect(iPhone *iphone)
{
if(AMDeviceConnect(iphone->handle) == 1)
{
iPhone_SetLastError("Device is in recovery mode. Must be activated with iTunes.");
return FALSE ;
}
if(AMDeviceIsPaired(iphone->handle) == 0)
{
iPhone_SetLastError("AMDeviceIsPaired failed.");
return FALSE;
}
if(AMDeviceValidatePairing(iphone->handle) != 0)
{
iPhone_SetLastError("AMDeviceValidatePairing failed.");
return FALSE;
}
if(AMDeviceStartSession(iphone->handle) == 1)
{
iPhone_SetLastError("AMDeviceStartSession failed.");
return FALSE;
}
if(AMDeviceStartService(iphone->handle, __CFStringMakeConstantString("com.apple.afc2"), &iphone->hService, NULL) != 0)
{
if(AMDeviceStartService(iphone->handle, __CFStringMakeConstantString("com.apple.afc"), &iphone->hService, NULL) != 0)
return FALSE;
}
if(AFCConnectionOpen(iphone->hService, 0, &iphone->hAFC) != 0)
{
iPhone_SetLastError("AFCConnectionOpen failed.");
return FALSE;
}
iphone->connected = TRUE;
return TRUE;
}
/** Waits for the specified iPhone to connect. */
void iPhone_WaitForConnect(iPhone *iphone)
{
while(iphone->connected == FALSE);
}
/** Retrieves the type of the file.
* @param iphone The iPhone on which to locate the file.
* @param path The UNIX style path to the file on the iPhone.
* @return AMD_FILE for regular file, AMD_DIR for directory, and AMD_LINK for hard or symbolic links.
*/
int iPhone_GetFileType(iPhone *iphone, char *path)
{
if(iphone->connected)
{
void *data = NULL;
int ret = AFCFileInfoOpen(iphone->hAFC, path, &data);
if(ret == 0 && data != NULL)
{
void *name, *val;
while(AFCKeyValueRead(data, &name, &val) == 0 && name != NULL && val != NULL)
{
if(strcmp(name, "st_ifmt") == 0)
{
if(strcmp(val, "S_IFREG") == 0) return AMD_FILE;
else if(strcmp(val, "S_IFDIR") == 0) return AMD_DIR;
else if(strcmp(val, "S_IFLNK") == 0) return AMD_LINK;
else return AMD_UNKNOWN;
}
}
AFCKeyValueClose(data);
}
}
return AMD_UNKNOWN;
}
/** Retrieves the file size of a file on an iPhone.
* @param iphone The iPhone on which to locate the file.
* @param path The UNIX style path to the file on the iPhone.
* @return The size of the file.
*/
long iPhone_GetFileSize(iPhone *iphone, char *path)
{
if(iphone->connected)
{
void *data = NULL;
int ret = AFCFileInfoOpen(iphone->hAFC, path, &data);
if(ret == 0 && data != NULL)
{
void *name, *val;
while(AFCKeyValueRead(data, &name, &val) == 0 && name != NULL && val != NULL)
{
if(strcmp(name, "st_size") == 0)
{
return atol(val);
}
}
AFCKeyValueClose(data);
}
}
return 0;
}