Solving priority inversion in assembly machines for discrete semiconductors Master thesis Laura Nij Bijvank 0213934 Research number 637 August 2010

2

Abstract Priority inversion can lead to a performance drop and lead to machines that come to a halt or even break down. Priority inversion can occur when threads of a concurrent program have to share data. Such a concurrent program runs on the assembly machines developed by ITEC, the Industrial Technology and Engineering Centre of the company NXP Semiconductors. In this thesis we examine the problem of priority inversion at ITEC. We investigate what causes priority inversion and which protocols for a solution are available. The choice of one protocol is justified by measurements. We describe the implementation the people at ITEC made and make some improvements to this implementation. Finally the proper use of the protocol is analyzed.

3

4

Acknowledgements I would like to thank Wiljan Derks for his supervision at NXP. Thanks also go to prof. dr. Jozef Hooman for his supervision of the project and his detailed feedback. I would also like to thank prof. dr. Frits Vaandrager for helping me finding a project and being my second supervisor. Finally I would like to thank everyone who supported me during my research and writing.

5

6

TABLE OF CONTENTS

1 Introduction ...... 11 1.1 Problem statement ...... 11 1.2 Research questions ...... 11 1.3 Approach ...... 12 2 Working environment at NXP ...... 13 2.1 NXP Semiconductors ...... 13 2.2 ITEC ...... 13 2.2.1 Die bonding ...... 14 2.2.2 Wire bonding ...... 14 2.2.3 Moulding ...... 15 2.2.4 Testing ...... 15 2.2.5 Quad ...... 16 2.3 Real‐Time Systems ...... 16 2.3.1 Types of real‐time systems ...... 16 2.3.2 Concurrency ...... 17 2.4 Symmetric multiprocessor system ...... 17 2.5 Windows XP ...... 18 2.5.1 Kernel ...... 18 2.5.2 Windows API ...... 18 2.5.3 Windows and real‐time processing ...... 18 2.6 Ada ...... 19 2.6.1 History of Ada ...... 19 2.6.2 Ada core and annexes ...... 20 2.6.3 The Ravenscar Profile ...... 20 2.6.4 GNAT ...... 20 3 The Ada Language ...... 23 3.1 Program Units ...... 23 3.1.1 Packages ...... 23 3.1.2 Subprograms ...... 24 3.1.3 Generic units ...... 24 3.1.4 Task units ...... 25 3.1.5 Protected units ...... 26 3.2 Loops ...... 26 3.3 Types...... 27 3.3.1 Subtypes ...... 27 3.3.2 Private types ...... 27 3.3.3 Limited types ...... 28 3.3.4 Tagged types ...... 28

7

3.3.5 Access types ...... 29 3.3.6 Arrays ...... 30 3.3.7 Records ...... 31 3.4 Pragmas ...... 31 3.4.1 Restrictions ...... 32 3.4.2 Import ...... 32 3.4.3 Suppress ...... 32 3.4.4 Inline ...... 32 4 ...... 34 4.1 Objects ...... 34 4.1.1 Programs, processes and threads ...... 34 4.1.2 Tasks ...... 34 4.1.3 Jobs ...... 35 4.2 Executing threads ...... 35 4.3 Priorities ...... 35 4.3.1 Rate Monotonic Scheduling ...... 36 4.3.2 Earliest Deadline First ...... 36 4.4 Windows ...... 37 4.4.1 Priority levels ...... 37 4.4.2 Scheduler ...... 39 4.5 Ada ...... 40 4.5.1 Priorities ...... 40 5 Data Sharing ...... 42 5.1 ...... 42 5.2 Interlocked operations ...... 42 5.3 Spinlocks ...... 43 5.4 Windows mechanisms ...... 43 5.4.1 ...... 43 5.4.2 Mutex ...... 44 5.4.3 Critical section objects ...... 44 5.4.4 Handles and Objects ...... 44 5.5 Ada mechanisms ...... 45 5.5.1 Atomic variables ...... 45 5.5.2 Volatile objects ...... 46 5.5.3 Rendezvous ...... 46 5.5.4 Protected Objects ...... 47 6 Priority Inheritance Protocols ...... 48 6.1 Basic priority inheritance protocol (PIP) ...... 49 6.2 and multiple blocking ...... 50 6.3 Priority Ceiling Protocol (PCP) ...... 50 6.4 Multiprocessor Priority Ceiling Protocol (MPCP) ...... 52 6.5 Immediate Ceiling Priority Protocol (ICPP) ...... 52 8

6.6 Other protocols ...... 53 7 ITEC priority inheritance ...... 54 7.1 Two types of mutexes ...... 54 7.2 Interlocked operations ...... 56 7.3 Basic mutexes ...... 57 7.3.1 Lock_Mutex ...... 58 7.3.2 Unlock_Mutex ...... 59 7.3.3 Is_Locked ...... 59 7.3.4 Close ...... 60 7.4 Priority inheritance mutexes ...... 60 7.4.1 Task Data ...... 60 7.4.2 Lock_Mutex ...... 62 7.4.3 Unlock_Mutex ...... 66 7.4.4 Is_Locked ...... 67 7.4.5 Close ...... 67 7.5 General subprograms ...... 68 7.5.1 Delete ...... 68 7.5.2 Get_Base_Priority ...... 68 7.5.3 Set_Base_Priority ...... 68 8 Protocol Choice ...... 70 8.1 Evaluation of the priority inheritance protocols ...... 70 8.2 About measuring ...... 70 8.2.1 Hardware ...... 71 8.2.2 Ada.Calendar.Time ...... 71 8.2.3 Ada.Real_Time.Time ...... 72 8.2.4 Scope ...... 73 8.2.5 HighRes_Timing.Time ...... 74 8.3 Counting priority raises ...... 74 8.4 Duration of setting priority ...... 75 8.5 Context switching ...... 76 8.5.1 Delay ...... 77 8.5.2 Sleep ...... 77 8.5.3 Suspension object ...... 77 8.5.4 Hold ...... 77 8.5.5 Measuring ...... 77 8.6 Conclusion ...... 80 9 Improvements ...... 83 9.1 Crashes ...... 83 9.2 Try_Lock_Mutex ...... 83 9.3 Task Data ...... 84 9.4 Interlocked functions...... 86 10 Performance measurements ...... 89 9

10.1 Collision and Raise count ...... 89 10.2 Speed of Windows functions ...... 90 10.3 Mutex performance ...... 91 11 Analysis ...... 93 11.1 Critical section duration ...... 93 11.2 Undesirable raises ...... 97 12 Conclusions ...... 99 12.1 Answers ...... 99 12.2 Future research ...... 100 12.2.1 Ada runtime locks ...... 100 12.2.2 Correctness ...... 100 12.2.3 Get more insight into priority inheritance ...... 100 12.2.4 Reduce the number of locks ...... 100 References ...... 102

10

1 INTRODUCTION

NXP is a company creating semiconductors, system solutions and software for a wide range of electronic devices [1]. ITEC (Industrial Technology and Engineering Centre) is a division of NXP which develops and supplies processes and equipment for the production of the discrete semiconductors (transistors, diodes). The control of this equipment highly depends on real‐time software. The ITEC software group makes this embedded software for the equipment made by ITEC [2]. The control of this equipment is realized on a system with a standard processor with hyper threading or a dual or quad core processor. The Windows XP operating system is used. More about NXP, ITEC and the system used can be found in chapter 2. The ITEC software group mainly uses the Ada programming language [3]. The main Ada language constructs are described in chapter 3. The Ada Runtime System (section 2.6.4.2) is used to execute Ada programs.

1.1 Problem statement The applications built for the equipment made by ITEC have about 30‐100 threads. Due to this large amount of threads, it is not always clear whether an implementation meets all time constraints. Threads are executed according to their priorities, but it is known that priority inversions occur. This means a high priority task has to wait for a lower priority task. This typically leads to a performance drop; machines may come to a halt or even break down. Reducing or eliminating priority inversion results in improved stability and performance. A well known solution to priority inversion is priority inheritance [4]. Unfortunately, priority inheritance is neither built‐in in windows XP nor in Ada. People at ITEC tried to implement priority inheritance in their own software. But this appeared not to be multiprocessor safe, leading to crashes with some complex applications. Additionally, the current ITEC solution has to avoid locks in the Ada runtime. These central locks do not use priority inheritance, which causes more priority inversion. To avoid this, the current implementation has to work around these runtime locks. To really take care of the priority inversion problem, the central locks in Ada runtime should also work with priority inheritance.

This leads us to the central question of this thesis: How can we avoid priority inversion in the systems