📜 ⬆️ ⬇️

Mono and OS MSVS


Import substitution! This is a very popular word now eclipsed even nanotechnology! It carries both great prospects and many problems. Not so long ago, it touched me. I was given the task to run our software on the operating system OS MSVS. It's a very interesting thing, considering that I last saw Linux about 8 years ago, and our software was written under .Net.

Familiarity with OS MSVS


So, Wikipedia says that the OS MSVS is the Mobile System of the Armed Forces. Namely, a general purpose protected operating system. Developed its organization VNIINS. The system is based on Linux in accordance with the requirements of the Ministry of Defense of the Russian Federation.

There are two branches of the system:


In each branch there are several versions called “changes”. The most recent certified versions are:

')
In the formulation of the task, no specific version of the system was indicated, therefore, after consulting with the technical support of VNIINS, the most current OS MSVS 5.0 TsAVM.11004-01 rev. â„–7.

About a month went to buy the official version and a few more days to select the hardware and install the system. We can definitely say that OS MSVS 5.0 is not installed on x86 processors and laptops with 2 video cards.

This is how the GUI of OSVS looks like:



The manufacturer indicates the following system parameters:


Having a little got acquainted with the system, I received the following information:


It can be assumed that this state of affairs is caused by difficulties in certifying the components of the system.

Well, the task has become more specific. Now you need to choose a solution. There are only two of them:

In order to save forces, time and nerves, the second option was chosen. Potential problems of this option are both the inability to normally start everything in principle, and the subsequent certification of software together with Mono. However, it is still faster and easier than rewriting everything.

Mono installation


What is Mono? Wikipedia suggests that this
A project to create a full-fledged implementation of the .NET Framework based on free software.
And also that
Mono implementations exist for the following operating systems: Windows, Linux, BSD (FreeBSD, OpenBSD, NetBSD), Solaris, Mac OS X, Apple iOS, Wii. Supported platforms: s390, SPARC, PowerPC, x86 / x86-64, IA64, ARM, Alpha, MIPS, HPPA.


Go to the project site and see there that you need to execute only 3 commands to install:

  1. rpm --import "http://keyserver.ubuntu.com/pks/lookup?op=get&search=0x3FA7E0328081BFF6A14DA29AA6A19B38D3D831EF"
  2. yum-config-manager --add-repo download.mono-project.com/repo/centos
  3. yum install mono-complete


The first command adds a signature key for access to the repository, the second sets up a repository, the third sets Mono.

The software is installed in the OS MSVS (as in the RHEL successor) in the form of RPM packages . For convenience of this process, the YUM package manager is often used. The OS MSVS includes a graphical package manager shell, but I used the console version. Packages are in repositories that can be located both on the local machine and somewhere on the network. By adding links to the repositories in the YUM package manager, you can quite conveniently update the system. As a rule, the repositories have already been added and configured in RHEL and its successors, however in the OS MSVS there is only one repository located on the installation CD.

The problems started already on the second team. It turned out that yum-config-manager missing from the system:


This means that you need to add the repository manually. They are located in the /etc/yum.repos.d directory. There you need to create a file <reponame>.repo . For example, mono.repo . In this file you need to add the following:

[mono_repository]
name=mono repository
baseurl=http://download.mono-project.com/repo/centos/
enabled=1
gpgcheck=0

After saving the file, I check that the repository is added by running the yum repolist . In this case, the disk with the distribution kit must be inserted and mounted. Or the repository on the disk should be disabled: enabled = 0 in the server.repo file.

However, now nothing happened:


Error [Errno -3] Error performing checksum says that YUM cannot calculate the checksum. As it turned out , the repository uses the sha256 hash function, which YUM cannot calculate. Experienced people write that in this case you need to put the python-hashlib . Since the repositories are not configured, I manually installed this version .

After that, the repositories are earned as needed:


But still installing Mono fails anyway .:


During installation, package dependencies are checked. It turned out that the installation of Mono from this repository requires that the system have library versions not lower than:



It would be possible to try to update all these libraries, however this may lead to problems in the work of other software using them.

StackOverFlow prompted me another solution: you need to try installing an earlier version of Mono. It turns out that there is an archive of versions . Experimentally it was possible to determine that the latest version of Mono, which is normally installed on OS MSVS 5.0 TsAVM.11004-01 meas. # 7 is version 2.10.2. The repository is here .

As a result, to install everything, you need to do the following:

1. Create (or correct) the <reponame>.repo repository file in /etc/yum.repos.d For example, mono.repo .
This file should contain the following:
[Mono]
name=Mono Stack (RHEL_5)
type=rpm-md
baseurl=http://origin-download.mono-project.com/archive/2.10.2/download/RHEL_5/
gpgcheck=1
gpgkey=http://origin-download.mono-project.com/archive/2.10.2/download/RHEL_5/repodata/repomd.xml.key
enabled=1

2. Run the yum install monotools-addon-server command to install the main libraries.
3. Run the yum install mono-addon-winforms-2.10.2-5.1.x86_64 to install the yum install mono-addon-winforms-2.10.2-5.1.x86_64 libraries.
4. Run the yum install mono-addon-libgdiplus0.x86_64 0:2.10-6.2 to install the GDI + implementation.

You can install other libraries. Description of the distribution kit can be found here . Mono is installed in /opt/novell/mono . Mono version 2.10.2 contains the following .Net versions: 2.0, 3.5 and 4.0.

You can check the installation as follows:
  1. configure the environment with the source /opt/novell/mono/bin/mono-addon-environment.sh
  2. find out version with mono --version


The result should be like this:


In addition, you can check the performance by running a couple of programs .

Porting problems


To work in a familiar environment, I installed the same version of Mono for Windows.

For debugging it is convenient to use the output in the console. To display it, you need to run the application with the parameter - --debug . For example, mono --debug helloworld.exe .

To isolate code intended only for Mono, I created two new configurations, MonoRelease and MonoDebug in VisualStudio.


In each of them, I added the compiler option /define MONO


Now you can use the following construction:

 #if MONO #else #endif 


From the first, of course, nothing worked. First of all - getting the name of the processes:
 var count = 0; foreach (var clsProcess in Process.GetProcesses()) { if(clsProcess.ProcessName.Contains(Process.GetCurrentProcess().ProcessName)) count++; } 


This code returns the number of the same processes running on the system. The problem was solved by ignoring exceptions from processes that we do not need.

 var count = 0; foreach (var clsProcess in Process.GetProcesses()) { #if MONO try { #endif if(clsProcess.ProcessName.Contains(Process.GetCurrentProcess().ProcessName)) count++; #if MONO } catch { } #endif } 

In this case, the code continued to perform its function.

Then on the form “left” buttons. It should be like this:


And it turned out like this:


This was decided by a small change in the arrangement of elements on the form:

 #if MONO tableLayoutPanel1.RowStyles[1].Height = 60; #endif 


There were also problems with the paths. In Linux, the '/' character is used to separate directories, and in Windows '\' . The problem is solved using System.IO.Path.DirectorySeparatorChar . This static field always has the correct value on any operating system.

But the main problem was marshaling. In our software, Marshal.StructureToPtr and Marshal.PtrToStructure are used to serialize specially tagged classes to a byte array and back to be transmitted over a network. Moreover, classes have a complex hierarchy and nesting. Microfoft .NET copes with this task with a bang, and Mono could not. I think this is a consequence of differences in working with memory.

As a result, we had to rewrite a very impressive part of the code, replacing the automatic serialization with the “manual” assembly of the class from the array.

Result


As a result, the problem was solved. Directly to porting took about 2 weeks. Another week took a study of the installation process Mono. And the month was the purchase of the operating system.

What's next?


And then you need to create your own repository, which will automatically install Mono and the software itself. After that, there should be certification ...

But, as usual, everything changed at the most interesting place. In the midst of work, it turned out that OS MSVS is no longer relevant. It is necessary to do everything on AstraLinux ... And this is a slightly different story.

Source: https://habr.com/ru/post/268131/


All Articles