Bentley Communities
Bentley Communities
  • Site
  • User
  • Site
  • Search
  • User
MicroStation
  • Product Communities
MicroStation
MicroStation Wiki Migrating MDL Applications To Native Code
    • Sign In

    • +MicroStation Wiki
    • +Administration Wiki
    • +Annotations Wiki
    • +Bentley View Wiki
    • +MicroStation PowerDraft
    • +Printing and Plotting
    • -Programming Wiki
      • A class to help create and modify text element
      • A Complete Example
      • A MicroStation VBA Example With Bentley ProjectWise
      • AddIn Development Using VB.NET
      • C# .NET Template with IPrimitiveCommandEvents Class
      • Capturing Graphics in Dynamic Views
      • Compiling MDL Applications
      • Database Manipulation
      • Debugging Native Code MDL Applications
      • Developing Code in VBA
      • Developing MicroStation Applications For DWG Files
      • Drag and Drop in MicroStation
      • Error: "Cannot save changes to VBA project 'Support' because it is read-only"
      • Getting And Setting Elements Using Graphic Groups In VBA [CS]
      • Getting Started with Visual Basic
      • How To Write A Recursive Routine In MicroStation VBA [CS]
      • Introducing Segment3D Methods In MicroStation V8 2004 Edition
      • Known issues in MDL and MicroStationAPI
      • Launching VBA Applications As Initapps Or Dgnapps [CS]
      • Learning MicroStation Addins Step by Step
      • MDL - Getting Started With XAttributes In MicroStation V8 XM Edition
      • MDL - Native Code Application Development
      • MDL Or MicroStation BASIC Choosing The Right Tool [TN]
      • MFC Dialog And Native Window Support
      • Microsoft Office VBA Patch Utility
      • MicroStation BASIC FAQ
      • MicroStation BASIC Limits [FAQ]
      • MicroStation Developer Documentation and Example Code
      • MicroStation Programming Advice
      • MicroStation SDK
      • MicroStation V8 Programming Tools Readme
      • MicroStation V8 VBA Programming Resources [CS]
      • MicroStation V8 XM Edition View Code Updates
      • MicroStation VBA Resources Revisited [CS]
      • Migrating Dimension Code To MicroStation V8
      • Migrating MDL Applications To Native Code
      • Mouse Wheel Events And The Visual Basic 6.0 IDE
      • Porting MDL Applications To MicroStation V8
      • Reading Elements From A Microsoft Access Database With VBA [CS]
      • Running MDL Applications
      • Scanning For MicroStation V8 Elements In VBA [CS]
      • Unleash A Workspace Wizard Automating Workspace Creation With MicroStation V8 And VBA [CS]
      • Using VBA To Detect The Current Or Last Used Command
      • Using VBA To Programmatically Export A VBA Project [CS]
      • Using VBA To Programmatically Import A VBA Projects Components And References [CS]
      • VBA -- Creating A Complex Application
      • VBA Interface Error: failed creating the comp manager - 0x80040583
      • VBA interface error: unable to get IDE
      • vba recording
      • Working With Levels In MicroStation VBA [CS]
      • Writing An MDL Application To Output Custom Placemarks To Google Earth
      • [V8i C++] PointCloud IPointCloudChannelDisplayHandler
    • +Visualization Wiki
    • Window List Dialog for Missing Tool Dialog Boxes

     
     Questions about this article, topic, or product? Click here. 

    Migrating MDL Applications To Native Code

    One of the new features of MicroStation V8 is the ability to build applications that are entirely Visual C based. This gives the advantage of using the native code debugger and other development tools. Most of these features have been possible for sometime by having little bits of MDL code that called the native code and kept things neatly seperated between MicroStation code and native code. Now all the callbacks are capable of being handled by native code implementations so the MDL layer disappears. You can convert your existing applications by following a few simple steps.

    • Step 1: The link between the MDL application MA and DLL. Yes, there is still an .ma file that is created and loaded. It contains the dialog resources as well as a resource of type DllMdlApp that tells the MA to load the DLL. You need to create this in a .r file that will be put into the application file. Typically this is done at the bottom of your command table resource file, but it can be in any resource file in your app. For example:

    #define  DLLAPP_EXAMPLE  1
      DllMdlApp  DLLAPP_EXAMPLE =
      {
      "MDLNAME",  "dllname"
      }

    • Step 2: Copy or rename the .mc (source code file) to a .c or .cpp extension. The extension of the file determines the compiler in a BMAKE rule so either a .c or .cpp file will use cl instead of mcomp. It is preferred to use cpp for all new development.
    • Step 3: Modifications to the source code. There are a few pieces that need to be added to the source code to make this work. You need to add a MdlCommandNumbers array. This array of structures will connect the command functions to the command numbers generated in you command table. ex:

    Private MdlCommandNumber commandNumbers [] =
      {
      {commandFunctionName, CMD_MYCOMMAND_NUMBER},
      0
      }

    Note that the 0 at the end is necessary to terminate the array.

    Next you need to add to the main function a call to register the command numbers. For example:

    mdlSystem_registerCommandNumbers (commandNumbers);

     

    You need to change the signature of the main function to be

    extern "C" DLLEXPORT int MdlMain (int argc, char *argv[])


    This will make the main function visible to the mdl system. You then need to remove all the cmdName and cmdNumber lines in the source code. Since these are not standard C syntax they weill cause compile errors.

    • Step 3A: If you plan on using cmdName as a keyword to "hide" commands in the application, the best choice is to use the HID key in the command table. In lieu of that, you can use cmdName as a keyword by first defining it:

    #define cmdName 1


    then building a parallel structure to the commandNumbers:

    Private MdlCommandName commandName[] = 
        {
        CommandNameFunction, "commandNamefunctionstring",
        0
        };

    • Step 4: The make file needs to now build a dll so the call to dlmlink.mki needs to be set up and integrated. For example:

    #------------------------------------------------ # Set up to use dlmlink.mki #------------------------------------------------  
    dlmObjs     = $(o)$(AppName)$(oext)  \
                   $(o)$(AppName)extra$(oext)

    DLM_OBJECT_DEST     = $(o)
    DLM_LIBDEF_SRC      = $(baseDir)
    DLM_NAME            = $(AppName)
    DLM_OBJECT_FILES    = $(dlmObjs)
    DLM_NO_DLS          = 1  #  Used DLLEXPORT in .cpp file instead of using a .dls
    DLM_NO_DEF          = 1
    DLM_NOENTRY         = 1
    DLM_DEST            = $(mdlapps)
    DLM_LIBRARY_FILES   = $(mdlLibs)toolsubs.lib 

    $(o)$(AppName)$(oext): $(baseDir)$(AppName).cpp

    $(o)$(AppName)extra$(oext): $(baseDir)$(AppName)extra.cpp


    #-------------------------------------------------------
    #  Use dlmlink.mki to link the DLM.
    #-------------------------------------------------------
    %include dlmlink.mki

    Note

    There are multiple possible destinations for the app. Three common possibilities are:

    DLM_DEST = $(mdlapps)
    DLM_DEST             = $(mdlAsNeeded)
    DLM_DEST             = $(mdlRequired)


    Since there is no longer a .mc file to .mo file, this step this must be removed from the make file. And lastly, if the DllMdlApp resource was defined in a new resource file it needs to be added to the resources that are Rlib'd to make the application (.ma) file.

    • Step 5: Now to compile this application you will need Visual C/C++ 7.1 and the compile environment set correctly. It is recommended that you use the MicroStation development shell since it will take care of these settings.

    The application will now be compiled into a .ma and .dll. All the dialogs and user interface are still built as MDL resources but are fully accessible from the native code. To debug the application will require using the VisualStudio tools. To set the debug environment the dll needs to be added to the list of dlls by using the Project->Settings->category->additional dlls. After setting this you can use the Edit->Breakpoints command to add the function name to debug and establish a break point.

    • Step 6: Add a DLM password. Once you have generated the password and added it to dlmpassw.h, add these lines just after mdlMain replacing MYAPP_PASSWORD with the correct name from dlmpassw.h:

    extern "C" DLLEXPORT
      #include <dlmpassw.h>
          MYAPP_PASSWORD


    Some notes about this process:

    Use of MicroStation built in variables:

    extern UserPrefs *userPrefsP; 
    extern  Tcb           *tcb;
    extern  Mgds_modes    mgds_modes;
    extern  int           mdlErrno;    /* mdl error number */
    extern  MSStateData   statedata;


    These are defined by including the msvar.fdf

    malloc in the application should be replaced by dlmSystem_malloc this is so any memory allocated with the application can be freeed with the application. This will force all memory calls to be through the dlmSystem family of functions which will automaticly associate the resource allocation with the task id. This allows the memory to be reclaimed when the application exits. The complete list of functions is:

    malloc -> dlmSystem_mdlMalloc 
    calloc   ->  dlmSystem_mdlCalloc
    realloc  ->  dlmSystem_mdlRealloc
    free     ->  dlmSystem_mdlFree
    strdup   ->  dlmSystem_mdlStrdup
    fopen    ->  dlmSystem_mdlFopen
    fclose   ->  dlmSystem_mdlFclose


    Be aware of MDL code that might have been accessing functions using mdlDialog_callFunction Since this function was used to make function calls between MDL applications.  This function is not valid in the native code environment.

    You cannot mix the use of DLS file and NO_DLS as defined in the Make file. The DLS file is used to create the export file, and is only necessary if you need to access the functions in the DLL from an MA. Thus it is usually not required, and generally preferable to use DLLEXPORT prefix for functions in the code. The prototype for mdlMain above takes this approach.

    While MDL applications are still the core of MicroStation, moving source code to native code can allow the developer access to many features of the Windows development environment. This entire conversion process can take as little as one or two hours on a simple MDL application.

    • native code
    • MDL
    • Share
    • History
    • More
    • Cancel
    • Dan Koval Created by Dan Koval
    • When: Thu, Sep 5 2013 4:28 PM
    • Revisions: 1
    • Comments: 0
    Recommended
    Related
    Communities
    • Home
    • Getting Started
    • Community Central
    • Products
    • Support
    • Secure File Upload
    • Feedback
    Support and Services
    • Home
    • Product Support
    • Downloads
    • Subscription Services Portal
    Training and Learning
    • Home
    • About Bentley Institute
    • My Learning History
    • Reference Books
    Social Media
    •    LinkedIn
    •    Facebook
    •    Twitter
    •    YouTube
    •    RSS Feed
    •    Email

    © 2023 Bentley Systems, Incorporated  |  Contact Us  |  Privacy |  Terms of Use  |  Cookies