[iOS memory management-compilation link & dynamic linker]

Preface

As far as I am concerned, I have very little knowledge about compilation and linking during iOS development, but this knowledge is still very important.

The compilation and linking process of iOS is not difficult, and it is quite similar to the assembly process of microcomputer principles. Today I will learn and understand the process of compilation and linking.
Reference: Self-cultivation of iOS programmers - compilation and linking process
Reference: iOS compilation process

Computer Languages

Computer languages ​​include machine language, assembly language and high-level language. For high-level languages ​​like OC, they are divided into compiled languages ​​and interpreted languages.
Insert image description here

  • Compiled language (one-time translation)
    • Features: One-time translation.
    • Compiled language programs can be run directly every time they are compiled by the compiler , as is the case with OC and Swift.
    • The advantage is that the execution speed is fast enough because there is no need to compile multiple times.
    • The disadvantage is that portability is poor. You need to link to the operating system libraries when compiling, and different libraries may be needed.
  • Interpreted languages ​​(step-by-step translation)
    • A program written in an interpreted language needs to be dynamically interpreted and executed by the interpreter every time it is run. For example, php,javascripta piece of code
      is interpreted and a piece of code is executed.
    • The advantage is that it has good portability and does not require complex system libraries.
    • The obvious disadvantage is that the execution speed is slow and it is not a one-time operation.

File extension

During the compilation and linking process of iOS, different file suffix names represent different file types and intermediate processes.

  • .iFile: .iFile is a file generated after the preprocessor processes the source code, which contains code after preprocessing operations such as macro expansion and conditional compilation.

  • .sFile: .sA file is an assembly code file generated by the assembler. It translates files generated by the preprocessor .iinto textual representations of machine instructions, one for each assembly instruction.

  • .oFile: .oA file is an object file generated by the compiler, also known as an object file. It contains machine instructions generated by the assembler as well as some symbol tables, relocation information, and other debugging information.

  • .mFile: .mFile is a common extension for Objective-C source code files. It contains Objective-C code and can be mixed with C and C++ code.

These files are generated at different stages during the compilation and linking process, and are converted and passed to each other throughout the process, ultimately generating executable files or library files.

Compilation and linking process

As mentioned above, OC/swift are both compiled languages. During execution, the compiler generates machine code. The machine code can be executed directly on the CPU, which is faster.

The compilation of OC is based on Clang/LLVM. A simple understanding is that LLVM is a collection of modular and reusable compilers and tool technologies. Clang is a subroutine of LLVM. C, C++, and OC are all subroutines of Clang. Its purpose is to compile better programs faster and more efficiently.

Compilation and linking process: preprocessing -> lexical analysis -> syntax analysis -> static analysis -> generate intermediate code and optimization -> assembly -> link =
preprocessing -> compile -> assembly -> link
Please add image description

Compile link

1. Preprocessing: macro macros, import header file replacement and processing of other precompilation instructions . 产生.i文件(all start with #)

2. Compile: Compile a series of preprocessed files 词法、语法、语义分析,并且优化后生成相应的汇编代码,产生.s文件;

3. Assembly: The assembler generates machine instructions from the assembly code ( 输出目标文件,产生.o文件just translate them one by one according to the comparison table of assembly instructions and machine instructions);

4. Linking: There may be other files in one file. Therefore, it is also necessary to combine the target files generated by compilation and the files provided by the system. This process is linking. After the link, 最后生成可执行文件.

After compilation and linking, the written code is converted into binary instructions that the computer can recognize.

Preprocessing (precompilation) -> Generate .i file

clang -E main.m -o main.i

Process precompilation directives starting with "#" in source code files

  • "#define" deletes and expands the corresponding macro definition.
  • Handles all conditional precompilation directives. like#if/#ifdef/#else/#endif。
  • "#include/#import"Contained files are recursively inserted here.
  • Remove all comments "// or /**/".
  • Add line number and file name identifiers. 如“# 1 "main.m"”, will be used for compilation and debugging.

To summarize the results of what the compiler does in the preprocessing phase:

  • Macro replacement (macro definitions used in source code will be replaced with corresponding content)
  • The header file introduction (#include,#import)uses the content of the corresponding file .h to replace the content of this line, so try to reduce #import in the header file, use @class instead, and put #import in the .m file. )
  • Handling conditional compilation directives(#if,#else,#endif)

Compile -> Generate .s file

clang -S main.i -o main.s

The compilation process is also divided into lexical analysis -> syntax analysis -> static analysis and finally optimization to generate the corresponding assembly code and obtain the .s file.

  • Lexical analysis: This step converts the code in the source file into a special markup stream. The source code is divided into characters and words one by one. The corresponding source file and specific line number where the source code is located are marked in the Loc at the end of the line, which is convenient. Locate the problem when reporting an error.
    Please add image description
  • Syntax analysis: This step is to parse the token stream generated by lexical analysis into an abstract syntax tree (AST). Similarly, each node in it is also marked with its position in the source code. At this time, the priority of the operation symbols has been determined; the multiple meanings of some symbols have also been determined, such as whether "*" is a multiplication sign or a pointer to take the content; if the expression is illegal, the brackets do not match, etc., errors will be reported.
    Please add image description
  • Static analysis: Analyze type declaration and matching issues, such as methods being called but not defined, variables being defined but not used, etc., to improve code quality.
    • Type analysis: At this stage clang will do checks, the most common ones are to check whether the program sends the correct message to the correct object and whether it calls normal functions on the correct value. NSObject*If you send a message to a simple object hello, clang will report an error. Likewise, if you set a property to an object that does not match its own type, the compiler will give a warning that it may be incorrectly used.
    • Other analysis: Check whether it is initialized multiple times.
  • Intermediate code generation and optimization: LLVM will compile and optimize the code, such as global variable optimization, loop optimization, tail recursion optimization, etc., and finally output assembly code.
  • Target code generation and optimization: Generate machine-specific assembly language based on intermediate language. and optimize assembly language.

Assembly->Generate .o file

clang -c main.s -o main.o

In this stage, the assembler converts the readable assembly code generated in the previous step into machine code. The final product is an object file ending in .o. Programs built with Xcode will find this file in the DerivedData directory.

Link

clang main.o -o main

This stage is to link the target file generated in the previous stage with the referenced static library , and finally generate an executable file. The linker solves the link between the target file and the library.

clang main.m生成可执行文件a.out(不指定名字默认为a.out),使用file a.outYou can see its type information using :

a.out: Mach-O 64-bit executable x86_64

It can be seen that the executable file type is Mach-Oof type, and the executable files on the MAC OS and iOS platforms are of this type.

Mach-O (Apple official documentation)

Please add image description

Dynamic and static libraries

Reference: iOS static library and dynamic library, see here.
The linking process is to link files and referenced static libraries and dynamic libraries. So what are dynamic libraries and static libraries, and how are they linked?

1. Static library

A static library is a static link library; it is a file package formed by compressing and packaging multiple target files. The following are types of static libraries

  • Windows.lib
  • Linux.a
  • Exclusive to MacOS.framework

static library

  • Advantages :: The static library will be integrated into the executable file when compiling and linking, allowing the program to run independently at runtime without relying on external libraries.
    Fast, due to integration into the executable file, calls to static libraries are usually faster than calls to dynamic libraries because no dynamic linking is required
  • Disadvantages : The generated executable program is larger. If multiple programs generated using static linking are run at the same time, they will occupy a large amount of memory space. Once the static library is compiled and linked into the executable file, code that wants to update or replace the static library needs to recompile the entire program.
    If multiple programs use the same static library, each program will contain a copy of the same library code, resulting in duplicate code

2. Dynamic library

  • Dynamic library is a dynamic link library, which is a way to implement a shared function library.
  • The dynamic library will not be copied to the target program during compilation. The target program will only store references to the dynamic library.
  • Only when the functions in the dynamic library are actually used will the functions be found, bound, and used.
  • The formats of dynamic libraries are: .framework, .dylib, .tbd……

Dynamic library :

  • Advantages : Save disk space, and when multiple programs using the same dynamic library are running at the same time, the library files will be shared through the process address space, and there will be no duplicate code in the memory. The update and replacement of the dynamic library is more convenient, and only needs to be replaced. Dynamic library files are sufficient, and there is no need to recompile the entire program. Dynamic libraries are dynamically linked when the program is running, making program files smaller and easier to distribute and deploy.
  • Disadvantages : Must rely on dynamic libraries, otherwise it cannot run. Dynamic libraries need to be loaded when the program starts, which may slightly increase the startup time of the program. Compatibility: Since different operating systems or different versions of dynamic libraries may have compatibility issues, special attention needs to be paid to version compatibility.

3. The difference between dynamic libraries and static libraries

  • static library
    • Loaded at compile time
    • Advantages: Code loading and execution are faster than dynamic libraries.
    • Disadvantages: waste of memory and disk space, difficult to update modules.
  • dynamic library
    • Load at runtime
    • Advantages: The size is much smaller than the static library and saves more memory.
    • Disadvantages: Code loading and execution speed are slower than static libraries.
  • Remark:
    • 最小单位16kThe size of the compiled dynamic library will be smaller than that of the static library.等于16k。
    • Switching to a dynamic library will result in some slowdowns, but it will be optimized through Lazy Binding technology.
    • Delayed binding: Find and record the memory address of the method when it is used for the first time, and the search process can be omitted for subsequent calls.

4. What is the relationship between dynamic libraries, static libraries, and frameworks?

  1. Libraries are compiled binaries.
  2. If the code needs to be provided for external use but does not want the code to be changed, the code can be encapsulated into a library and only the header file is exposed for calling.
  3. If you want to improve the compilation speed, you can encapsulate part of the code into a library and only need to link it during compilation.
  4. Libraries all need to be linked. There are static and dynamic ways to link libraries, so static libraries and dynamic libraries are produced.

frameworkIt is a file packaging method that encapsulates header files, binary files, and resource files together to facilitate management and distribution. So there are both dynamic library and static library formats.framework;
Please add image description

Summarize

Compilation and linking is the process from the beginning of an iOS file to becoming an executable file. We will not study the principle, but it is still necessary to master the entire process.

Guess you like

Origin blog.csdn.net/weixin_61639290/article/details/131735461