Developing jailbreak tweak - objective-c

I have searched everywhere for a solution to this but cannot find one.
My tweak, developed in Theos is very simple, I want to disable the mute button in the phone app. I have found the private framework I think I need and the code that is called.
I have added a message so i can see if this routine is called, but is not.
Although my code compiles and installs on the phone, it never runs.
I have tried a basic springboard tweak and that is fine, so I must be doing something wrong with the framework or subroutine called?
(I have also added com.apple.mobilephone to my plist as suggested somewhere)
Here is my MAKEFILE
include theos/makefiles/common.mk
TARGET_IPHONEOS_DEPLOYMENT_VERSION=7.0
TWEAK_NAME = Disablemute
TARGET = iphone:7.0:7.0
ARCHS = armv7
Disablemute_FILES = Tweak.xm
Disablemute_FRAMEWORKS = UIKit
Disablemute_PRIVATE_FRAMEWORKS = TelephonyUtilities CoreTelephony
include $(THEOS_MAKE_PATH)/tweak.mk
Here is the tweak.mk code
#import <PrivateFrameworks/TelephonyUtilities/TUCall.h>
#import <UIKit/UIKit.h>
%hook TUCall
- (void)setMuted:(BOOL)arg1 {
//%orig;
%log;
UIAlertView *alert = [[UIAlertView alloc] initWithTitle:#"Welcome"
message:#"Welcome to your iPhone Burt!"
delegate:nil
cancelButtonTitle:#"Thanks"
otherButtonTitles:nil];
[alert show];
[alert release];
}
%end
So the private framework is TelephonyUtilities and the header file is TUCall.h, the function is -void SetMuted:(BOOL)arg1;
Can anyone help please.

Related

IBAction makes errors on theos compiling

I'm new to Objective-C programming and I want to make a simple tweak about VLC for iOS.app but I can't compile.
Here's my code :
#import <UIKit/UIKit.h>
%hook VLCMovieViewController
-(IBAction)playPause
{
if([_mediaPlayer isPlaying]) {
UIAlertView *pause = [[UIAlertView alloc] initWithTitle:#"PAUSED" message:#"Your movie is paused" delegate:nil cancelButtonTitle:nil otherButtonTitles:#"OK !", nil];
[_listPlayer pause];
[pause show];
[pause release];
}
else
{
UIAlertView *play = [[UIAlertView alloc] initWithTitle:#"PLAYING" message:#"Your movie is playing" delegate:nil cancelButtonTitle:nil otherButtonTitles:#"OK !", nil];
[_listPlayer play];
[play show];
[play release];
}
}
%end
I don't find any mistakes in my codes but when I try to compile, theos returns me an error :
Preprocessing Tweak.xm...
Compiling Tweak.xm...
Tweak.xm:6:8: error: expected unqualified-id
static IBAction (*_logos_orig$_ungrouped$VLCMovieViewController$playPause)(VLCMovieViewController*, SEL); s...
^
<built-in :24:22: note: expanded from here
#define IBAction void)__attribute__((ibaction)
^
1 error generated.
make[2]: *** [obj/Tweak.xm.708dff35.o] Error 1
make[1]: *** [internal-library-all_] Error 2
make: *** [VLCTweak.all.tweak.variables] Error 2
Have you any clue to make it working ?
Many thanks in advance
You don't need to use IBAction with Theos, as you don't use Interface Builder.
IBAction is only a way to tell Xcode and Interface Builder to link UI elements to your code.
Replacing -(IBAction)playPause by -(void)playPause should work

iOS: My Alert message is displayed twice, but the code is only executed once

Here is my code that calls "displayAlert". The problem is not only do I get an error message (wait_fences: failed to receive reply: 10004003) but the "alert" is displayed twice!
if(gSiteID.globalSiteID.length == 0) { // user didn't choose site
[self displayAlert:NSLocalizedString(#"Missing Site ID", nil) andData:NSLocalizedString(#"You must choose a site from the View Sites page",nil)];
return;
}
This the code for "displayAlert":
- (void) displayAlert: (NSString *) title andData: (NSString *) errorMsg {
UIAlertView *alert = [[UIAlertView alloc]
initWithTitle: title
message: errorMsg
delegate:nil
cancelButtonTitle: #"OK"
otherButtonTitles: nil];
[alert show];
return;
}
I have searched SO and Google and found nothing that is specific to my issue. What am I doing wrong?
Are you testing this on a real device or the simulator? wait_fences: failed to receive reply usually means something bad happened with the debugger's connection to your device, or that you sat at a breakpoint for a really long time and it timed out. Are you sure that the code only executes once, and that nothing else could call that method? Stick breakpoints in your if statement and in your displayAlert:andData: method and see what happens. Run through your logic and find all the cases when that display alert method can be called and stick breakpoints on all of them.
I found the problem: indeed I was calling it twice from different .cs files (do you see the egg on my face?). Jack Lawrence please post your answer to the question, since you hit it on the head.

NSLog ignored on devices

I am trying to redirect all NSLog output to be able to see all my logs in a UITextView inside the app (for debug purposes, and maybe later to log everything using TestFlight). I can't use the well-known DLog because I want to catch logs from frameworks I don't own.
I'm doing this by 'redirecting' stderr to a pipe and reading from this pipe.
Anyway, this works well on the simulator and on the device when the app is launched from within Xcode.
But, this does not work when the app is launched "by hand" on the device.
It seems that NSLog calls have no effect on the device: I don't read anything from the pipe. However, if I manually write on stderr : fprintf(stderr, "test") I can read it from the pipe, so the problem is not with stderr but rather with the NSLog function.
Why does it do nothing on devices ? Is there a way to make it write on stderr even on the device ?
If it is not possible to use NSLog on devices, is there another way to gather logs from external frameworks ?
Thank you.
NSLog goes to the system log on devices. You can access the system log using the C API asl (Apple System Log); also check out this blog post.
However if you're using TestFlight it's much easier to just replace/append those NSLog statements with the TFLog statement.
TFLog(#"This comment is live on TestFlight.");
If you want some UILogging, you could consider using ULog, a UIAlertView based Logging #define directive.
// ULog will show the UIAlertView only when the DEBUG variable is set
#ifdef DEBUG
# define ULog(fmt, ...) { UIAlertView *alert = [[UIAlertView alloc] initWithTitle:[NSString stringWithFormat:#"%s\n [Line %d] ", __PRETTY_FUNCTION__, __LINE__] message:[NSString stringWithFormat:fmt, ##__VA_ARGS__] delegate:nil cancelButtonTitle:#"Ok" otherButtonTitles:nil]; [alert show]; }
#else
# define ULog(...)
#endif
(source: http://overbythere.co.uk/blog/2012/01/alternatives-nslog)

Get values from a different class

I want to replace the title and message with the return values from a different class and also put it into an if statement that will see if the return value matches a value i state. can you help me out a little bit, this is my code below, I'm using theos by the way
the 3 methods i want to get the values for are
-(id)title
-(id)message
-(id)_appName
from the SBBulletinBannerItem class
any help is appreciated
%hook SBBulletinBannerController
- (void)_handleBannerTapGesture:(id)reply
{
reply = [[UIAlertView alloc] initWithTitle:#"title" message:#"message" delegate:self cancelButtonTitle:#"Close" otherButtonTitles:#"Reply", nil];
[reply show];
[reply release];
}
%end
It sounds like you'll want to use delegates and protocols. You may have seen this using standard Cocoa and Cocoa Touch classes. This is how you respond to events in a UITableView.
You can find examples of implementing this yourself here.

iOS Reachability Not Recognizing When Host is Removed

I am building an application and trying to check and see if a device is still available on the network (by connecting to the devices IPAddress). I am using reachability to confirm that it is available.
When I network access for the iOS device (turn on airplane mode for example) everything works properly, but if I remove the device from the network, reachability does not seem to notice the change.
It seems like reachability is caching the results, and not seeing the update.
Don't use reachability then!
Use this bit of code instead which works a treat;
NSString *connected = [NSString stringWithContentsOfURL:[NSURL URLWithString:#"http://www.google.com"]];
wait(25000);
if (connected == NULL) {
NSLog(#"Not Connected");
//Code to show if not connected
UIAlertView *alert = [[UIAlertView alloc] initWithTitle:nil message:#"Oops! You aren't connected to the Internet."
delegate:self cancelButtonTitle:#"OK" otherButtonTitles:nil];
[alert show];
[alert release];
} else {
NSLog(#"Connected Successfully!");
//Any other code for successful connection
}
The SCReachability API only checks if the local hardware is configured such that it could reach the specified address; it does not actually attempt to reach it. To determine if the target is alive and kicking, you must attempt to open a connection to it.
Check out this answer. While the pixelbit's answer is viable, burtlo is right to bring up that just waiting 25 seconds isn't a great idea. Using the NSURLConnection is much cleaner.
Apple updated the Reachabilty class file. You can test it with latest Xcode.
here is link:
Apple Reachabilty Sample Code
I tested with Xcode 8.3.1 on iPhone 6 version 10.3.1.
It will notify user for change in network status.