Monday, October 13, 2008

Revit 64bit & The Revit API

Revit 64bit has arrived for subscription customers, and is available from Autodesk's website. There has been some confusion around this release, as when you create a deployment of Revit off the disk, it asks if you would like to make a 64bit deployment. This is apparently a typo, and isn't really a 64bit version of Revit. So now the real deal is out, and should speed things up for Vista/XP 64bit users, especially those with 4gb of RAM. However, for API developers, it brings a couple of kinks to work around. Now the framework runs in 64bit mode, so there is the chance that some of your existing external commands will break. There are a couple of things that you can do if your external command, which was working fine in 32bit revit does not work in 64bit. Change the security permissions for Framework64 If you are receiving an error message that talks about System Security exceptions, then you should see my post on the issue of security with the 64bit .net framework. As the security settings are different in the 64bit framework, these will need to be updated as required. (Only if your application needs this, and you have access to change these settings, ie a LAN environment). Compile for Any CPU. Anthony Hauck pointed out to me that the Getting Started SDK guide has been updated to include: Compatibility of API applications with 64-bit Revit Most API applications can be built with settings that allow them to be used either with 32-bit Revit or 64-bit Revit. Use the following settings to build your project in this manner: For C# project, go to project property->Build tag, select platform target as “Any CPU”. For VB.Net project, go to project property->Compile tag, select platform as “Any CPU”. For C++/CLI project, open property page and go to Configuration properties->General->Common Language Runtime support, select /clr:safe. Note that there are some Microsoft components (such as OleDB provider for Microsoft Jet) that are not supported for 64-bit. All SDK samples are set up to work with either 32-bit or 64-bit Revit, except those samples that have dependencies to unsupported Microsoft components. For more information see this Microsoft resource: http://msdn.microsoft.com/en-us/library/ms241064(VS.80).aspx

Microsoft .Net should do all the hard work in compiling your code for 64bit compatibility (See Matt Masons post explaining why). And, as long as you don't access any 32-bit 3rd party DLL's in your application, everything should run smoothly. Compile for 64bit CPU. This should not be necessary, and is not ideal, as you cannot use it at all in a 32bit version of Revit, however it is usefull to try if only purely as a debugging tool. A problem I ran into was that one of my external commands just did not start, it did not display any error mesage, just didn't run. There was an entry in my journal file stating:
 ' 1:< DBG_INFO: Could not load file or assembly
'file:///L:\Revit\bwtools\Plotting\Plotting.dll' or one of its dependencies.
An attempt was made to load a program with an incorrect format.:
line 93 of .\Source\APIManagedExecuteCommand.cpp. 
This is the generic error for when a 32bit program is called from a 64bit environment. After some experimentation, it seems that this was caused by my application Microsofts 32bit DSOFile.dll. To get my program to start at all, I had to compile for x64, this didn't fix my problem totally (I'll discuss this below) however it allowed me to start the dll and debug to pinpoint where exactly the error was occuring. To do this in visual studio head to the properties page of your project and go to the 'build' section. Then set the platform target to 'x64'. I then specified a different output directory (as we have 64bit and 32bit users on our network) and built the project. It was then a matter of updating the target users revit.ini file to point to the 64bit build instead of the 32bit build. I did this by updating my ini edting program to detect if the operating system is vista, if so check if revit is in the program files, or program files (x86) directory and copy the text accordingly. This got my macro to start, but it then crashed when calling the DLL. This however gave me the chance to pinpoint the location of the exception. Find 64bit version of 3rd party DLL's The problem I described above, was due to me accessing a 3rd party COM DLL which is compiled for 64bit. The only way I am able to rectify this is by finding a 32bit version of the required DLL and installing it on the users machine. This will be different for each situation, but one thing to keep in mind that regsvr32.exe, the tool used to reference DLL's in the registry does not have a regsvr64.exe counterpart, contrary to common logic. Unfortunately microsoft decided to keep the name the same, but simply store it in a different directory. So C:\Windows\SysWOW64\regsvr32.exe is the 64bit dll registrar. Summary The process has been made really easy by the revit team, assuming one thing - you do not use a 3rd party 32bit dll. So for 99% of external commands, the switch is simple, and chances are you won't have to do anything! Unfortunately for the other 1% the reality of 64bit development is that you are going to run into problems with external 32bit references, and will probably be cast into DLL-hell. So test those commands! If anyone has had other issues with 64bit Revit they would like to share please comment this article or join this discussion at AUGI.

64bit System.Security.SecurityException errors

In a follow up to a previous post of mine, which talked about the intranet security levels and how to change the permissions. I have one change to make. When running your application in the 64bit framework, permissions are different, so the previously posted batch file will not do anything to solve your issues. To fix it, add '64' onto the end of the Framework part of the caspol path. for example: echo y|C:\WINDOWS\Microsoft.NET\Framework64\v2.0.50727\caspol.exe -m -ag 1.2 -url file://server/share/* FullTrust I came across this problem using the new Revit 64bit with some of my API programs that access C drive or use the network.