C Pointers and Memory


(James Campbell) #1

How are arrays passed to C in Linux ? I tried unwrapping an optional array
in an if statment and passing it to c. it seemed like the array was
deallocated however if I stored it in a local var in the function before
the if statment it worked perfectly fine, sureley this shouldn't work
either ?

···

*___________________________________*

*James⎥Head of Trolls*

*james@supmenow.com <james@supmenow.com>⎥supmenow.com <http://supmenow.com>*

*Sup*

*Runway East *

*10 Finsbury Square*

*London*

* EC2A 1AF *


(Dmitri Gribenko) #2

Would you mind pasting the code example?

Dmitri

···

On Thu, Jul 28, 2016 at 1:27 PM, James Campbell via swift-users <swift-users@swift.org> wrote:

How are arrays passed to C in Linux ? I tried unwrapping an optional array
in an if statment and passing it to c. it seemed like the array was
deallocated however if I stored it in a local var in the function before the
if statment it worked perfectly fine, sureley this shouldn't work either ?

--
main(i,j){for(i=2;;i++){for(j=2;j<i;j++){if(!(i%j)){j=0;break;}}if
(j){printf("%d\n",i);}}} /*Dmitri Gribenko <gribozavr@gmail.com>*/


(James Campbell) #3

So this:

if let data = someArrayGeneratingFunction() {
  cFunction(UnsafeMutablePointer(data))
}

Has issues with the array passed to c getting corrupted, but this doesn't:

let data = someArrayGeneratingFunction()

if let data = data {
  cFunction(UnsafeMutablePointer(data))
}

···

*___________________________________*

*James⎥Head of Trolls*

*james@supmenow.com <james@supmenow.com>⎥supmenow.com <http://supmenow.com>*

*Sup*

*Runway East *

*10 Finsbury Square*

*London*

* EC2A 1AF *

On 28 July 2016 at 21:32, Dmitri Gribenko <gribozavr@gmail.com> wrote:

On Thu, Jul 28, 2016 at 1:27 PM, James Campbell via swift-users > <swift-users@swift.org> wrote:
> How are arrays passed to C in Linux ? I tried unwrapping an optional
array
> in an if statment and passing it to c. it seemed like the array was
> deallocated however if I stored it in a local var in the function before
the
> if statment it worked perfectly fine, sureley this shouldn't work either
?

Would you mind pasting the code example?

Dmitri

--
main(i,j){for(i=2;;i++){for(j=2;j<i;j++){if(!(i%j)){j=0;break;}}if
(j){printf("%d\n",i);}}} /*Dmitri Gribenko <gribozavr@gmail.com>*/


(Dmitri Gribenko) #4

Neither piece of code is guaranteed to work. (You are just getting
lucky that the second one happens to work.) Array-to-pointer
conversion only extends the lifetime of the array until the immediate
function call returns. So after UnsafeMutablePointer(data) returns,
the array can be freed.

Use someArrayGeneratingFunction.withUnsafeMutableBuffer { ... } instead.

Dmitri

···

On Fri, Jul 29, 2016 at 12:55 AM, James Campbell <james@supmenow.com> wrote:

So this:

if let data = someArrayGeneratingFunction() {
  cFunction(UnsafeMutablePointer(data))
}

Has issues with the array passed to c getting corrupted, but this doesn't:

let data = someArrayGeneratingFunction()

if let data = data {
  cFunction(UnsafeMutablePointer(data))
}

--
main(i,j){for(i=2;;i++){for(j=2;j<i;j++){if(!(i%j)){j=0;break;}}if
(j){printf("%d\n",i);}}} /*Dmitri Gribenko <gribozavr@gmail.com>*/


(James Campbell) #5

​Do you know of any resources to brush up on the pointer aspect of swift ? ​

···

*___________________________________*

*James⎥Head of Trolls*

*james@supmenow.com <james@supmenow.com>⎥supmenow.com <http://supmenow.com>*

*Sup*

*Runway East *

*10 Finsbury Square*

*London*

* EC2A 1AF *

On 29 July 2016 at 09:10, Dmitri Gribenko <gribozavr@gmail.com> wrote:

On Fri, Jul 29, 2016 at 12:55 AM, James Campbell <james@supmenow.com> > wrote:
> So this:
>
> if let data = someArrayGeneratingFunction() {
> cFunction(UnsafeMutablePointer(data))
> }
>
> Has issues with the array passed to c getting corrupted, but this
doesn't:
>
> let data = someArrayGeneratingFunction()
>
> if let data = data {
> cFunction(UnsafeMutablePointer(data))
> }

Neither piece of code is guaranteed to work. (You are just getting
lucky that the second one happens to work.) Array-to-pointer
conversion only extends the lifetime of the array until the immediate
function call returns. So after UnsafeMutablePointer(data) returns,
the array can be freed.

Use someArrayGeneratingFunction.withUnsafeMutableBuffer { ... } instead.

Dmitri

--
main(i,j){for(i=2;;i++){for(j=2;j<i;j++){if(!(i%j)){j=0;break;}}if
(j){printf("%d\n",i);}}} /*Dmitri Gribenko <gribozavr@gmail.com>*/


(Zhao Xin) #6

Have you read
https://developer.apple.com/library/tvos/documentation/Swift/Conceptual/BuildingCocoaApps/InteractingWithCAPIs.html#//apple_ref/doc/uid/TP40014216-CH8-ID17
?

Zhaoxin

···

On Fri, Jul 29, 2016 at 4:55 PM, James Campbell via swift-users < swift-users@swift.org> wrote:

​Do you know of any resources to brush up on the pointer aspect of swift ?

*___________________________________*

*James⎥Head of Trolls*

*james@supmenow.com <james@supmenow.com>⎥supmenow.com
<http://supmenow.com>*

*Sup*

*Runway East *

*10 Finsbury Square*

*London*

* EC2A 1AF *

On 29 July 2016 at 09:10, Dmitri Gribenko <gribozavr@gmail.com> wrote:

On Fri, Jul 29, 2016 at 12:55 AM, James Campbell <james@supmenow.com> >> wrote:
> So this:
>
> if let data = someArrayGeneratingFunction() {
> cFunction(UnsafeMutablePointer(data))
> }
>
> Has issues with the array passed to c getting corrupted, but this
doesn't:
>
> let data = someArrayGeneratingFunction()
>
> if let data = data {
> cFunction(UnsafeMutablePointer(data))
> }

Neither piece of code is guaranteed to work. (You are just getting
lucky that the second one happens to work.) Array-to-pointer
conversion only extends the lifetime of the array until the immediate
function call returns. So after UnsafeMutablePointer(data) returns,
the array can be freed.

Use someArrayGeneratingFunction.withUnsafeMutableBuffer { ... } instead.

Dmitri

--
main(i,j){for(i=2;;i++){for(j=2;j<i;j++){if(!(i%j)){j=0;break;}}if
(j){printf("%d\n",i);}}} /*Dmitri Gribenko <gribozavr@gmail.com>*/

_______________________________________________
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


(James Campbell) #7

No I haven't thats a big help thank you !

···

*___________________________________*

*James⎥Head of Trolls*

*james@supmenow.com <james@supmenow.com>⎥supmenow.com <http://supmenow.com>*

*Sup*

*Runway East *

*10 Finsbury Square*

*London*

* EC2A 1AF *

On 29 July 2016 at 10:40, Zhao Xin <owenzx@gmail.com> wrote:

Have you read
https://developer.apple.com/library/tvos/documentation/Swift/Conceptual/BuildingCocoaApps/InteractingWithCAPIs.html#//apple_ref/doc/uid/TP40014216-CH8-ID17
?

Zhaoxin

On Fri, Jul 29, 2016 at 4:55 PM, James Campbell via swift-users < > swift-users@swift.org> wrote:

​Do you know of any resources to brush up on the pointer aspect of swift
? ​

*___________________________________*

*James⎥Head of Trolls*

*james@supmenow.com <james@supmenow.com>⎥supmenow.com
<http://supmenow.com>*

*Sup*

*Runway East *

*10 Finsbury Square*

*London*

* EC2A 1AF *

On 29 July 2016 at 09:10, Dmitri Gribenko <gribozavr@gmail.com> wrote:

On Fri, Jul 29, 2016 at 12:55 AM, James Campbell <james@supmenow.com> >>> wrote:
> So this:
>
> if let data = someArrayGeneratingFunction() {
> cFunction(UnsafeMutablePointer(data))
> }
>
> Has issues with the array passed to c getting corrupted, but this
doesn't:
>
> let data = someArrayGeneratingFunction()
>
> if let data = data {
> cFunction(UnsafeMutablePointer(data))
> }

Neither piece of code is guaranteed to work. (You are just getting
lucky that the second one happens to work.) Array-to-pointer
conversion only extends the lifetime of the array until the immediate
function call returns. So after UnsafeMutablePointer(data) returns,
the array can be freed.

Use someArrayGeneratingFunction.withUnsafeMutableBuffer { ... } instead.

Dmitri

--
main(i,j){for(i=2;;i++){for(j=2;j<i;j++){if(!(i%j)){j=0;break;}}if
(j){printf("%d\n",i);}}} /*Dmitri Gribenko <gribozavr@gmail.com>*/

_______________________________________________
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


(Chris McIntyre) #8

Hi guys,

I’m having issues with Swift pointers. I feel like the Interactive With C APis document only gets you half way there.

For example, look at this from the docs

If you have declared a function like this one:

func takesAMutablePointer(x: UnsafeMutablePointer<Float>) {
    // ...
}
You can call it in any of the following ways:

var x: Float = 0.0
var p: UnsafeMutablePointer<Float> = nil
var a: [Float] = [1.0, 2.0, 3.0]
takesAMutablePointer(nil)
takesAMutablePointer(p)
takesAMutablePointer(&x)
takesAMutablePointer(&a)
Seem simple enough. But then I was trying to figure out Core Data validation, which takes an AutoreleasingUnsafeMutablePointer<AnyObject?> and I can’t figure out what to pass to it.

I tried to create a simple test in a Playground:

func takesAPointer(p: AutoreleasingUnsafeMutablePointer<AnyObject?>){
    return
}

var myString = "Hello"

takesAPointer(p: &myString)

Then I get an error stating 'Cannot pass immutable type “AnyObject?” as inout argument’.

Everything seems to match the example from the docs. I have a var (so it should be mutable) and I’m using the ampersand, but still I’m getting an error.

Another problem. I have a specific byte pattern I want to create. For arguments sake, lets call it 0x123ABC, and I have it as an Int. I want to access the individual bytes (i.e. 12, 3A, BC).

The struct reference for UnsafePointer<T> doesn’t talk much about initializing it. Most of the initializers take a pointer. I tried the init(_ bitPattern:) initializer, and was able to create a pointer, but it seemed to point to the address 0x123ABC rather than the address *of* 0x123ABC. I tried creating a buffer with malloc, and it gives me an UnsafeMutablePointer but now I can’t figure out how to copy my bytes to this buffer.

So clearly there’s something I’m just not grocking about Swift pointers. Does anyone know of a more remedial tutorial that is updated for Swift 3? I’d like to continue to work in pure Swift, but it just isn’t clicking.

···

--
Chris McIntyre

On Jul 29, 2016, at 6:11 AM, James Campbell via swift-users <swift-users@swift.org> wrote:

No I haven't thats a big help thank you !

___________________________________

James⎥Head of Trolls

james@supmenow.com <mailto:james@supmenow.com>⎥supmenow.com <http://supmenow.com/>
Sup

Runway East >

10 Finsbury Square

London

> EC2A 1AF

On 29 July 2016 at 10:40, Zhao Xin <owenzx@gmail.com <mailto:owenzx@gmail.com>> wrote:
Have you read https://developer.apple.com/library/tvos/documentation/Swift/Conceptual/BuildingCocoaApps/InteractingWithCAPIs.html#//apple_ref/doc/uid/TP40014216-CH8-ID17 ?

Zhaoxin

On Fri, Jul 29, 2016 at 4:55 PM, James Campbell via swift-users <swift-users@swift.org <mailto:swift-users@swift.org>> wrote:
​Do you know of any resources to brush up on the pointer aspect of swift ? ​

___________________________________

James⎥Head of Trolls

james@supmenow.com <mailto:james@supmenow.com>⎥supmenow.com <http://supmenow.com/>
Sup

Runway East >

10 Finsbury Square

London

> EC2A 1AF

On 29 July 2016 at 09:10, Dmitri Gribenko <gribozavr@gmail.com <mailto:gribozavr@gmail.com>> wrote:
On Fri, Jul 29, 2016 at 12:55 AM, James Campbell <james@supmenow.com <mailto:james@supmenow.com>> wrote:
> So this:
>
> if let data = someArrayGeneratingFunction() {
> cFunction(UnsafeMutablePointer(data))
> }
>
> Has issues with the array passed to c getting corrupted, but this doesn't:
>
> let data = someArrayGeneratingFunction()
>
> if let data = data {
> cFunction(UnsafeMutablePointer(data))
> }

Neither piece of code is guaranteed to work. (You are just getting
lucky that the second one happens to work.) Array-to-pointer
conversion only extends the lifetime of the array until the immediate
function call returns. So after UnsafeMutablePointer(data) returns,
the array can be freed.

Use someArrayGeneratingFunction.withUnsafeMutableBuffer { ... } instead.

Dmitri

--
main(i,j){for(i=2;;i++){for(j=2;j<i;j++){if(!(i%j)){j=0;break;}}if
(j){printf("%d\n",i);}}} /*Dmitri Gribenko <gribozavr@gmail.com <mailto:gribozavr@gmail.com>>*/

_______________________________________________
swift-users mailing list
swift-users@swift.org <mailto:swift-users@swift.org>
https://lists.swift.org/mailman/listinfo/swift-users

_______________________________________________
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


(Lou Zell) #9

Hi guys,

I’m having issues with Swift pointers. I feel like the Interactive With C
APis document only gets you half way there.

For example, look at this from the docs

If you have declared a function like this one:

   1. func takesAMutablePointer(x: UnsafeMutablePointer<Float>) {
   2. // ...
   3. }

You can call it in any of the following ways:

   1. var x: Float = 0.0
   2. var p: UnsafeMutablePointer<Float> = nil
   3. var a: [Float] = [1.0, 2.0, 3.0]
   4. takesAMutablePointer(nil)
   5. takesAMutablePointer(p)
   6. takesAMutablePointer(&x)
   7. takesAMutablePointer(&a)

Seem simple enough. But then I was trying to figure out Core Data
validation, which takes an AutoreleasingUnsafeMutablePointer<AnyObject?>
and I can’t figure out what to pass to it.

I tried to create a simple test in a Playground:

func takesAPointer(p: AutoreleasingUnsafeMutablePointer<AnyObject?>){

    return

}

var myString = "Hello"

takesAPointer(p: &myString)

Try this:

import Foundation
func takesAPointer(p: AutoreleasingUnsafeMutablePointer<AnyObject?>){
    return
}
let myString : NSString? = "Hello"
var obj : AnyObject? = myString
takesAPointer(&obj)

Then I get an error stating 'Cannot pass immutable type “AnyObject?” as
inout argument’.

Everything seems to match the example from the docs. I have a var (so it
should be mutable) and I’m using the ampersand, but still I’m getting an
error.

Another problem. I have a specific byte pattern I want to create. For
arguments sake, lets call it 0x123ABC, and I have it as an Int. I want to
access the individual bytes (i.e. 12, 3A, BC).

Is something like this what you're looking for:
let a = UInt16((0x123ABC >> 16) & 0xFF)
let b = UInt16((0x123ABC >> 8) & 0xFF)
print(String(a, radix: 16))
print(String(b, radix: 16))

···

On Fri, Jul 29, 2016 at 8:40 PM, Chris McIntyre via swift-users < swift-users@swift.org> wrote:

The struct reference for UnsafePointer<T> doesn’t talk much about
initializing it. Most of the initializers take a pointer. I tried the
init(_ bitPattern:) initializer, and was able to create a pointer, but it
seemed to point to the address 0x123ABC rather than the address *of*
0x123ABC. I tried creating a buffer with malloc, and it gives me an
UnsafeMutablePointer but now I can’t figure out how to copy my bytes to
this buffer.

So clearly there’s something I’m just not grocking about Swift pointers.
Does anyone know of a more remedial tutorial that is updated for Swift 3?
I’d like to continue to work in pure Swift, but it just isn’t clicking.

--
Chris McIntyre

On Jul 29, 2016, at 6:11 AM, James Campbell via swift-users < > swift-users@swift.org> wrote:

No I haven't thats a big help thank you !

*___________________________________*

*James⎥Head of Trolls*

*james@supmenow.com <james@supmenow.com>⎥supmenow.com
<http://supmenow.com/>*

*Sup*

*Runway East *

*10 Finsbury Square*

*London*

* EC2A 1AF *

On 29 July 2016 at 10:40, Zhao Xin <owenzx@gmail.com> wrote:

Have you read
https://developer.apple.com/library/tvos/documentation/Swift/Conceptual/BuildingCocoaApps/InteractingWithCAPIs.html#//apple_ref/doc/uid/TP40014216-CH8-ID17
?

Zhaoxin

On Fri, Jul 29, 2016 at 4:55 PM, James Campbell via swift-users < >> swift-users@swift.org> wrote:

​Do you know of any resources to brush up on the pointer aspect of swift
? ​

*___________________________________*

*James⎥Head of Trolls*

*james@supmenow.com <james@supmenow.com>⎥supmenow.com
<http://supmenow.com/>*

*Sup*

*Runway East *

*10 Finsbury Square*

*London*

* EC2A 1AF *

On 29 July 2016 at 09:10, Dmitri Gribenko <gribozavr@gmail.com> wrote:

On Fri, Jul 29, 2016 at 12:55 AM, James Campbell <james@supmenow.com> >>>> wrote:
> So this:
>
> if let data = someArrayGeneratingFunction() {
> cFunction(UnsafeMutablePointer(data))
> }
>
> Has issues with the array passed to c getting corrupted, but this
doesn't:
>
> let data = someArrayGeneratingFunction()
>
> if let data = data {
> cFunction(UnsafeMutablePointer(data))
> }

Neither piece of code is guaranteed to work. (You are just getting
lucky that the second one happens to work.) Array-to-pointer
conversion only extends the lifetime of the array until the immediate
function call returns. So after UnsafeMutablePointer(data) returns,
the array can be freed.

Use someArrayGeneratingFunction.withUnsafeMutableBuffer { ... } instead.

Dmitri

--
main(i,j){for(i=2;;i++){for(j=2;j<i;j++){if(!(i%j)){j=0;break;}}if
(j){printf("%d\n",i);}}} /*Dmitri Gribenko <gribozavr@gmail.com>*/

_______________________________________________
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users

_______________________________________________
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users

_______________________________________________
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


(Bryan Chan) #10

Personally I like swiftdoc.org as a reference:

http://swiftdoc.org/v3.0/type/UnsafeMutablePointer/

Click on the initializers and function names to read the description of
what each of them does.

You can use a UnsafeMutableBufferPointer to help initialize your memory
(which you have to allocate first):

var memory = UnsafeMutablePointer<Int8>(allocatingCapacity: 4)
var buf = UnsafeMutableBufferPointer<Int8>(start: memory, count: 4)
for i in 0...3 {
    buf[i] = Int8(0x10 * (i + 1)) // [ 16, 32, 48, 64 ]
}
CFunctionThatTakesACharPointer(memory, 4)

···

--
Bryan Chan

On Fri, Jul 29, 2016 at 11:40 PM, Chris McIntyre via swift-users < swift-users@swift.org> wrote:

Another problem. I have a specific byte pattern I want to create. For
arguments sake, lets call it 0x123ABC, and I have it as an Int. I want to
access the individual bytes (i.e. 12, 3A, BC).

The struct reference for UnsafePointer<T> doesn’t talk much about
initializing it. Most of the initializers take a pointer. I tried the
init(_ bitPattern:) initializer, and was able to create a pointer, but it
seemed to point to the address 0x123ABC rather than the address *of*
0x123ABC. I tried creating a buffer with malloc, and it gives me an
UnsafeMutablePointer but now I can’t figure out how to copy my bytes to
this buffer.