Apportable trivial conversion errors - apportable

I'm encountering errors while cross-compiling using Apportable which ends with "scons: building terminated because of errors."
When I say apportable load, it goes into the compilation step and then spits out 21 errors (and a few warnings). I think there may already be a way to debug most of them, but I do not know how to tackle them because I am new to apportable.
Here is an example of 3 of the 21 errors. What can I do to get this to work?
Thanks for the help!
error: no visible #interface for
'NSDateComponents' declares the selector 'setTimeZone:'
[dc setTimeZone:[NSTimeZone timeZoneWithName:(NSString *)serverTimeZoneName]];
~~ ^~~~~~~~~~~
error: use of undeclared identifier 'NSFontAttributeName'
CGSize textSize = [self.activityLabel.text sizeWithAttributes:#{NSFontAttributeName:[UIFont systemFontOfSize:[UIFont systemFontSize]]}]; ~~~~~ ^~~~~
error: no visible #interface for 'UITableView' declares the selector 'endUpdates'
[self.tableView endUpdates];
~~~~~~~~~~~ ^~~~~~~~~~

The simplest thing to do when you are trying to get your app working the first time using Apportable is to disable the lines of code that aren't compiling. For example:
#if !defined(ANDROID)
[dc setTimeZone:[NSTimeZone timeZoneWithName:(NSString *)serverTimeZoneName]];
#endif
Once you have it compiling, linking, and running, it is much easier to determine the best way to deal with the differences between Apportable and iOS.

Related

Is it OK to define an opaque type as an empty struct to get around linker warning in C++/CLI?

I have a C++ project that is configured to use CLR. The project contains a subclass of CTreeCtrl, i.e. a class provided by Microsoft that I have no control over. Since the public interface of CTreeCtrl heavily uses the type HTREEITEM, it is unavoidable that the subclass also makes use of the type - but since the type is "opaque", the subclass only passes around HTREEITEM references without actually doing anything with the referenced objects.
By "opaque", I mean that HTREEITEM is only visible as a forward-declared type. Here's the declaration that I see in CommCtrl.h:
struct _TREEITEM;
typedef struct _TREEITEM *HTREEITEM;
Unfortunately, in a release build this usage of HTREEITEM generates the following linker warning:
foo.obj : warning LNK4248: unresolved typeref token (01000017) for '_TREEITEM'; image may not run
Here is the MSDN link for the warning. I have searched the net for a solution to get rid of the warning, but have found nothing - only confirmation that over the years other people have encountered this warning in relation to HTREEITEM as well.
Now I have been thinking of a workaround myself. Given that
My class only gets HTREEITEM references from CtreeCtrl and passes them back to CtreeCtrl, without any kind of interpretation or function calls
HTREEITEM is merely a pointer to _TREEITEM
It follows that all that my class ever does is pass around pointers to _TREEITEM. My idea for a workaround therefore is this: Why not define _TREEITEM as an empty struct in my project, like this:
struct _TREEITEM
{
};
Obviously this makes the linker happy since it now sees the complete type. The fact that the struct definition is incorrect is not relevant since my class is only passing around pointers to _TREEITEM, i.e. all that the compiler needs to know is the size of a HTREEITEM.
I have tried this workaround and it seems to work, not only at compile time but at runtime as well. So what do you think of this workaround? Did I overlook something? I certainly won't be offended if you call it an ugly hack :-)
FWIW: I am currently on Visual Studio 2010.

Xamarin Linker : Default constructor not found for type Cirrious.CrossCore.IoC.MvxPropertyInjector

With a skeleton project with FirstView from HotTuna package, and with Build linker behavior set to "Link all assemblies", I get the following error:
System.MissingMethodException: Default constructor not found for type Cirrious.CrossCore.IoC.MvxPropertyInjector
Using NuGet package v3.1.1 for all MvvmCross (4 packages)
LinkerPleaseInclude file does have the line
[MonoTouch.Foundation.Preserve(AllMembers = true)]
Using the latest stable build:
On PC:
Xamarin for VS 1.12.278
Xamarin.iOS 1.12.278
Mac:
Xamarin.iOS 7.2.2.2
Of course with Linker behavior of SDK only, it runs fine. Any suggestions anyone?
Solved; So, with the basic project, there were three consecutive errors in the following order:
System.MissingMethodException: Default constructor not found for type Cirrious.CrossCore.IoC.MvxPropertyInjector
can be resolved either by --linkskip=Cirrious.Core (ugly), or by including the following in LinkerPleaseInclude.cs
public void Include(MvxPropertyInjector injector){
injector = new MvxPropertyInjector ();
}
Next error is:
Cirrious.CrossCore.Exceptions.MvxException: Failed to construct and initialize ViewModel for type {0} from locator MvxDefaultViewModelLocator - check MvxTrace for more information
This one is difficult; Simple fix is to ofcourse to do a --linkskip=portableLibrary, or to crate an instance of the ViewModel somewhere (perhaps in LinkerPleaseInclude.cs); problem with the second approach at-least in my case is, most of my VM doesn't have a parameter less constructor, and obviously using IOC in this case wouldn't help.
Final Error:
System.ArgumentNullException: missing source event info in MvxWeakEventSubscription
Parameter name: sourceEventInfo
Either use --linkskip=System (ugly), or add the following to LinkerPleaseInclude.cs
public void Include(INotifyPropertyChanged changed)
{
changed.PropertyChanged += (sender, e) => {
var test = e.PropertyName;
};
}
This was enough for my basic project to run with LinkAllAssemblies, Using LLVM optimizer, and Use SGen collector.
Hope this will help anyone looking for a solution.
I hit this when my XCode was out of sync with the latest Xamarin on my Mac. Upgrading XCode to the latest resolved the problem.

Multiply Defined Symbols with Precompiled Header?

Well, I have been struggling with this for days now. I am writing a custom game DLL for CryENGINE from scratch, and I cannot even get the solution compile with one simple class (Game.cpp) and a precompiled header (StdAfx.h).
Both Game.cpp and StdAfx.cpp will compile perfectly on their own, but compiling the solution throw tons of multiply defined errors. The class is simple because the definitions are just placeholders.
Game.h
#if !defined __GAME__H__
#define __GAME__H__
#pragma once
class CGame : public IGame
{
public:
CGame();
VIRTUAL ~CGame();
//IMPLEMENT: IGame Interface, all methods declared.
};
#endif
Game.cpp
#include "StdAfx.h" //PreComp header
#include "Game.h"
//Define all methods, each one has a simple definition.
StdAfx.h
#if !defined __STDAFX__H__
#define __STDAFX__H__
#pragma once
//Various CryENGINE includes
#endif
Output
error LNK2005: "struct SSystemGlobalEnvironment * gEnv" (? gEnv##3PEAUSSystemGlobalEnvironment##EA) already defined in StdAfx.obj
error LNK2005: "public: static long volatile _CryMemoryManagerPoolHelper::allocatedMemory" (?allocatedMemory#_CryMemoryManagerPoolHelper##2JC) already defined in StdAfx.obj
error LNK2005: "public: static long volatile _CryMemoryManagerPoolHelper::freedMemory" (?freedMemory#_CryMemoryManagerPoolHelper##2JC) already defined in StdAfx.obj
error LNK2005: "public: static long volatile _CryMemoryManagerPoolHelper::requestedMemory" (?requestedMemory#_CryMemoryManagerPoolHelper##2JC) already defined in StdAfx.obj
error LNK2005: "public: static int volatile _CryMemoryManagerPoolHelper::numAllocations" (?numAllocations#_CryMemoryManagerPoolHelper##2HC) already defined in StdAfx.obj
The list goes on...
What really throws me off is that each one will compile just fine individually, so syntax and references are good. What could possibly cause multiply defined errors when the solution is compiled as a whole?
I really appreciate help on this frustrating issue, thank you.
I'm not sure the errors are caused by the precompiled header, but here is the correct way to set up the precompiled header:
Right-click on the project name in Solution Explorer, select Properties, go to Configuration Properties | C/C++ | Precompiled Headers and set the Precompiled Header setting to Use (/Yu). Leave the other two settings below it to the default.
Right-click on StdAfx.cpp, go to the same setting and set it to Create (/Yc).
Well, I figured it out. There is a clever complex include that does not belong in the precompiled header:
#include <Platform_Impl.h>
This was causing all my problems, and by moving it to Game.cpp, everything is fine.

How to force Monotouch AOT Compiler to see a nested generic method?

I've had to jump through hoops, but I've almost managed to get ServiceStack working on iOS with Monotouch in my project. One runtime JIT exception is holding out:
System.ExecutionEngineException: Attempting to JIT compile method 'ServiceStack.Text.Json.JsonTypeSerializer:GetWriteFn<int> ()' while running with --aot-only.
The offending code is quite simple:
internal WriteObjectDelegate GetWriteFn<T>()
{
return JsonWriter<T>.WriteFn();
}
As a test, I modified the SS code to make the internal methods and types public and included the following in the startup code of my project (to actually get called).
var ick = ServiceStack.Text.Json.JsonWriter<int>.WriteFn();
var erk = ServiceStack.Text.Json.JsonTypeSerializer.Instance.GetWriteFn<int>();
This still doesn't alert the AOT for some reason, I get the exception when the code above executes! Is this because the generic parameter is a value type? Or is it because these are static classes and methods? How can I force Monotouch to AOT the methods above?
The SS code in question is in JsonTypeSerializer.cs and JsonWriter.Generic.cs at:
https://github.com/ServiceStack/ServiceStack.Text/tree/master/src/ServiceStack.Text/Json
There are some generic limitations in monotouch now. I think you should check your code to one of them.

Visual C++ / STL exception not caught

The following method (in a Visual Studio 2008 ref class) contains a simple error that I thought would be caught - but instead it causes the process to abort with a "Debug Assertion Failed!" message box (msg includes the offending STL vector src line#). This occurs whether compiled in Debug or Release mode. The process in this case is Excel.exe and the method is accessed via COM interop.
Can someone tell me why this error doesn't get trapped ?
String^ FOO()
{
try {
std::vector<int> vfoo;
vfoo.push_back(999);
return vfoo[1].ToString(); //!!!! error: index 1 not valid
}
catch(std::exception& stdE) { // not catching
return "Unhandled STL exception";
}
catch(System::Exception^ E) { // not catching
return "Unhandled .NET exception: " + E->Message;
}
catch(...) { // not even this is catching
return "Unhandled exception";
}
}
In the Debug configuration you'll get an assert that's enabled by the iterator debugging feature. Designed to help to find mistakes in your use of the standard C++ library. You can use the Call Stack window to trace back to the statement in your code that triggered the assert. The feature is controlled by the _HAS_ITERATOR_DEBUGGING macro, very few reasons to ever turn that off in the Debug build. Well, none.
In the Release configuration, you'll run into the Checked Iterators feature, part of the Secure CRT Library initiative introduced at VS2005 and controlled by the _SECURE_SCL macro. It has a hook built in to get the debugger to stop, much as the above, to show you why it bombed. But not without a debugger, if none is attached then it immediately terminates your program with SEH exception code 0xc0000417. That's kinda where the buck stops, the DLL version of the CRT was built with _SECURE_SCL in effect and you have no option to not use that DLL when you write managed code. Building with /MT is required to completely turn it off and that's not possible in C++/CLI.
This tends to drive C++ programmers pretty nutty, catch (...) {} is a blessed language feature even though the odds of restoring program state are very close to zero. There is a back-door however (there's always a back-door), the argument validation code emits the error condition through a function pointer. The default handler immediately aborts the program with no way to catch it, not even with SetUnhandledExceptionFilter(). You can replace the handler with the _set_invalid_parameter_handler() function. That needs to be done by your Main() method, something like this:
#include "stdafx.h"
#include <stdlib.h>
using namespace System;
#pragma managed(push, off)
void no_invalid_parameter_exit(const wchar_t * expression, const wchar_t * function,
const wchar_t * file, unsigned int line, uintptr_t pReserved) {
throw new std::invalid_argument("invalid argument");
}
#pragma managed(pop)
int main(array<System::String ^> ^args)
{
_set_invalid_parameter_handler(no_invalid_parameter_exit);
// etc...
}
Which will run one of your catch handlers. The managed one, leaving no decent breadcrumbs to show what happened, but that's normal for native C++ exceptions.
"Debug Assertion Failed!" sounds like, well, an assert()-like check. These are NOT exceptions.
I actually use assert()-style checking for everything that constitutes a programming error, and use exceptions for runtime errors. Maybe Microsoft follows a similar policy; an "index out of bounds" is clearly a programming error, not something that is caused by e.g. your disk getting full.

Resources