5

I am trying to ignore SIGPIPE signal that is thrown by a third party SDK I am using in my Swift application. How do I make my application ignore SIGPIPE signal globally?

Natasha
  • 53
  • 4

1 Answers1

5

The syntax is the same as in a C program:

signal(SIGPIPE, SIG_IGN)

The problem is that SIG_IGN is not defined in Swift. For C programs, it is defined in <sys/signal.h> as

#define SIG_IGN     (void (*)(int))1

but this integer to pointer conversion is not imported into Swift, so you have to define it yourself:

let SIG_IGN = CFunctionPointer<((Int32) -> Void)>(COpaquePointer(bitPattern: 1))
signal(SIGPIPE, SIG_IGN)

For Swift 2 (Xcode 7) the following should work:

typealias SigHandler = @convention(c) (Int32) -> Void
let SIG_IGN = unsafeBitCast(COpaquePointer(bitPattern: 1), SigHandler.self)
signal(SIGPIPE, SIG_IGN)

As of Swift 2.1 (Xcode 7.1), SIG_IGN is defined as a public property and you can simply write

signal(SIGPIPE, SIG_IGN)
Martin R
  • 529,903
  • 94
  • 1,240
  • 1,382
  • Thanks! I was struggling with swift syntax trying to create CFunctionPointer to represent SIG_IGN. I am testing your solution right now. Thanks again for quick reply! – Natasha Dec 11 '14 at 19:14
  • I'm struggling on this issue, where exactly do I put the code you provided? I tried it on the entry point on my swift app but I still get the signal :-/ – JustADev Mar 01 '15 at 18:59
  • Never mind me I ended up editing an obj-c file of the lib I'm using as per this answer http://stackoverflow.com/a/450130/3104287 Though if you think I must do it your way in swift please let me know :) – JustADev Mar 01 '15 at 19:09
  • @Martin R do you know how to do this in Swift 2.1? I copied your code but there's an error saying `'CFunctionPointer' is unavailable: use a function type '@convention(c) (T) -> U'. I don't really understand how to convert it to said function, so I'm wondering if you could help me here? – Anna Fortuna Feb 16 '16 at 09:58
  • For swift 2.1, just use signal(SIGPIPE, SIG_IGN) worked for me. – ZYiOS Mar 21 '16 at 15:31
  • @MartinR hmm, now `signal(SIGPIPE, SIG_IGN)` is the first thing executed in `application(_ application: didFinishLaunchingWithOptions launchOptions:)` and I still managed to catch the app crashing on SIGPIPE. I'll try some investigation – iOS Unit Jun 14 '18 at 11:03
  • @iOSUnit: It seems that the *debugger* (lldb) by default breaks on all signals, compare https://stackoverflow.com/a/12649223/1187415 or https://stackoverflow.com/q/10431579/1187415. – So you can simply "continue" or change the signal handling behavior with `process handle -p true -s false SIGPIPE` – Martin R Jun 15 '18 at 09:42
  • Hi, for swift 5 is there any new grammar? thanks! – ch271828n Dec 14 '20 at 09:07
  • @ch271828n: It should still be `signal(SIGPIPE, SIG_IGN)` – are the any problems with it in Swift 5? – Martin R Dec 14 '20 at 09:10