MTLRenderPipelineAttachmentDescriptor swift linker error - swift

I have linker error:
Undefined symbols for architecture arm64:
_OBJC_CLASS_$_MTLRenderPipelineAttachmentDescriptorArray
with following code
var pipelineStateDescriptor = MTLRenderPipelineDescriptor()
pipelineStateDescriptor.label = "Test1"
pipelineStateDescriptor.sampleCount = 1
pipelineStateDescriptor.vertexFunction = vertexFunction
pipelineStateDescriptor.fragmentFunction = fragmentFunction
var colorDescriptor = MTLRenderPipelineAttachmentDescriptor()
colorDescriptor.pixelFormat = .FormatBGRA8Unorm
pipelineStateDescriptor.colorAttachments[0] = colorDescriptor
Is any solution for this?

Update:
This bug is no more actual in ios8 beta 3.
In your project build settings set "Optimization level" to "-Ofast", like this
Here is short info on compiler optimization flags
It seems to be a bug of beta sdk. I made a project in which I try to use Metal with Swift, go check it out https://github.com/haawa799/METAL_Playground.
Hope it will help.

Related

Can't compile RxCocoa for Apple Watch

I've been trying to compile an already existing iOS project containing a target for an Apple Watch extension.
The project uses RxSwift/RxCocoa which, reading at the official documentation, is compatible with watchOS.
The project compiles and runs successfully on Apple Watch simulator, but it fails on a real Apple Watch, with the following error:
Cannot find 'CGRectType' in scope
Cannot find 'CGPointType' in scope
Cannot find 'CGSizeType' in scope
The reason of this is that these three constants, declared in a class extension inside RxCocoa, are declared like this:
#if arch(x86_64) || arch(arm64)
let CGRectType = "{CGRect={CGPoint=dd}{CGSize=dd}}"
let CGSizeType = "{CGSize=dd}"
let CGPointType = "{CGPoint=dd}"
#elseif arch(i386) || arch(arm)
let CGRectType = "{CGRect={CGPoint=ff}{CGSize=ff}}"
let CGSizeType = "{CGSize=ff}"
let CGPointType = "{CGPoint=ff}"
#endif
Do you know if there's any way to make it work, as this library is supposed to be compatible with watchOS?
I guess that you are still using am old version of the library (not compatible with recent version of the watchOS)
The right definition on the library should be something like
#if arch(x86_64) || arch(arm64)
let CGRectType = "{CGRect={CGPoint=dd}{CGSize=dd}}"
let CGSizeType = "{CGSize=dd}"
let CGPointType = "{CGPoint=dd}"
#elseif arch(i386) || arch(arm) || arch(arm64_32)
let CGRectType = "{CGRect={CGPoint=ff}{CGSize=ff}}"
let CGSizeType = "{CGSize=ff}"
let CGPointType = "{CGPoint=ff}"
#endif
According to this two discussion thread in the library site
Fix build for new arm64_32 architecture
Xcode 10 GM: Use of unresolved identifier 'CGRectType'
It should be fixed in the latest version of the library

Unresolved identifier 'CALayerContentsGravity' in Swift 4

The below code works well with "Swift 3" but giving error of "unresolved identifier CALayerContentsGravity" in "Swift 4"
static func create(image: UIImage, size: Double) -> CALayer {
let containerLayer = createContainerLayer(size)
let imageLayer = createContainerLayer(size)
containerLayer.addSublayer(imageLayer)
imageLayer.contents = image.cgImage
imageLayer.contentsGravity = CALayerContentsGravity.resizeAspect
return containerLayer
}
In swift4 CALayerContentsGravity is not working.
To set contentsGravity of layer you should use constant string which is available in swift4.
imageLayer.contentsGravity = kCAGravityResizeAspect
Hope it will work.
i had this problem after I imported the Cosmos pod. I spoke to the author and he said I need to check the pod's target and the Swift language it used.
When I check the Cosmos target the Swift version was 4 but my main project used Swift 4.2. Once I changed the Cosmos pod's version from 4 to 4.2 the error went away.
suggestion from Cosmos author
This is how you check the Cosmos pod Swift version
It needs to match what's in your main project's target:

Value of type 'AVCapturePhotoOutput' has no member 'outputSettings'

Curious, what would this be in Swift 4?
stimageout = AVCapturePhotoOutput()
stimageout?.outputSettings = [AVVideoCodecKey : AVVideoCodecJPEG]
Currently, it errors with Value of type 'AVCapturePhotoOutput' has no member 'outputSettings' which is odd since I don't have memory of Apple changing this.
This is not "begging for help"-type question. I'm just curious if Apple changed this and the steps I need to do in order to fix this issue.
Thanks in advance. :)
The problem is outputSettings is a property on AVCaptureStillImageOutput, not AVCapturePhotoOutput.
AVCaptureStillImageOutput is deprecated in iOS 10, so for iOS 10+, use AVCapturePhotoOutput instead. To set settings using the new API, you can use an AVCapturePhotoSettings object.
let stimageout = AVCapturePhotoOutput()
let settings = AVCapturePhotoSettings()
settings.livePhotoVideoCodecType = .jpeg
stimageout.capturePhoto(with: settings, delegate: self)
Apple's AVCapturePhotoOutput Documentation: https://developer.apple.com/documentation/avfoundation/avcapturephotooutput

Calling getsectiondata from Swift

This question and answer describe how to read data from a Mach-O section with Objective-C on modern OS X/macOS versions: Crash reading bytes from getsectbyname
The described answer works. I'm trying to implement the same thing with Swift. I can't make it work.
I have the following in "Other linker flags": -Wl,-sectcreate,__LOCALIZATIONS,__base,en.lproj/Localizable.strings,-segprot,__LOCALIZATIONS,r,r.
This Swift code gets me the a pointer to the embedded data, until I try to run the code outside Xcode and ASLR breaks it:
var size: UInt = 0
let _localizationSection = getsectdata(
"__LOCALIZATIONS",
"__base",
&size)
To get around the ASLR problem, according to the above question and answer, and based on my own testing, I should be using getsectiondata instead. It works great in Objective-C, but I'm having no luck in Swift. The following is the only thing I've managed to get past the compiler, but it returns nil:
var size: UInt = 0
var header = _mh_execute_header
let localizationSection = getsectiondata(
&header,
"__LOCALIZATIONS",
"__base",
&size)
Is taking a copy of _mh_execute_header the problem and is there any way to avoid it? I need an UnsafePointer<mach_header_64>, but using &_mh_execute_header as the first parameter to getsectiondata causes a compilation error.
I'm using Swift 3.0, and running my code on macOS 10.12.
The difference between the linked-to Objective-C code
void *ptr = getsectiondata(&_mh_execute_header, ...);
and your Swift translation
var header = _mh_execute_header
let localizationSection = getsectiondata(&header, ...)
is that the latter passes the address of a copy of the global
_mh_execute_header variable to the function, and apparently that
is not accepted. If you modify the Objective-C code to
struct mach_header_64 header = _mh_execute_header;
void *ptr = getsectiondata(&header, ...);
then it fails as well (and actually crashed in my test).
Now the problem is that _mh_execute_header is exposed to Swift
as a constant:
public let _mh_execute_header: mach_header_64
and one cannot take the address of a constant in Swift. One possible
workaround is to define
#import <mach-o/ldsyms.h>
static const struct mach_header_64 *mhExecHeaderPtr = &_mh_execute_header;
in the bridging header file, and then use it as
let localizationSection = getsectiondata(mhExecHeaderPtr, ...)
in Swift.
Another option is to lookup the symbol via dlopen/dlsym
import MachO
if let handle = dlopen(nil, RTLD_LAZY) {
defer { dlclose(handle) }
if let ptr = dlsym(handle, MH_EXECUTE_SYM) {
let mhExecHeaderPtr = ptr.assumingMemoryBound(to: mach_header_64.self)
var size: UInt = 0
let localizationSection = getsectiondata(
mhExecHeaderPtr,
"__LOCALIZATIONS",
"__base",
&size)
// ...
}
}

UIDevice.currentDevice().identifierForVendor!.UUIDString Swift 3 migration

I have the following code in swift 2
let deviceid = UIDevice.currentDevice().identifierForVendor!.UUIDString
This fails to compile. I tried following suggestions from the auto-fix in xCode and I came up with this.
let deviceid = UIDevice.currentDevice.identifierForVendor!.UUIDString
However it still does not compile. It says value of type 'UUID' has no member UUIDString'
My advice - for these kind of issues - get straight into a playground
let deviceid = UIDevice.current.identifierForVendor?.uuidString