• 沒有找到結果。

Performance of the Replace Operation

4. A Java-based, General-purpose Component Framework for Dynamic Reconfiguration

4.3.2 Performance of the Replace Operation

The dynamically reconfigurable TCP can be upgraded while it is running. When the TCP1 component is in the established state, that is, the TCP connection has been established, we replace it with the TCP2 component.

Fig. 4-4 shows the overall performance of the replace operation using the serialization-only approach, serialization with preloading, and native programming approach. The result is averaged from 100 iterations and the standard deviations are also shown as bars. In addition, two techniques are used to measure the performance: the getrusage function of Linux and System.currentTimeMillis method of Java. The getrusage function measures the actual

Figure 4-4: Overall performance of serialization and native programming approaches.

processor time consumed by the Java environment while the System.currentTimeMillis method measures execution time experienced by the user. Notice that the result of System.currentTimeMillis depends on the system load of the machine.

In Fig. 4-4, the reconfiguration lasts 212.8 ms using the serialization only approach while the same reconfiguration lasts only 33.95 ms using the native programming approach. The performance of serialization with preloading lies between the two. Detailed analysis of the performance is shown in Fig. 4-5, indicating the performance of eight major steps of the replace operation measured by the getrusage function. No matter which approach is used,

state transfer is always the most time-consuming step. However, the native programming approach spends only one ninth of the serialization only approach in this step. In addition, since the stack inspection and thread resumption are both less than 1 ms, they have little effect on the overall performance. Notice that the native programming approach spends slightly more time than the serialization approach in reference duplication and handler

Figure 4-5: The detailed performance of serialization and native programming approaches.

invoking steps. This is because in these two steps the native programming approach leads to some class loadings that have already occurred in the state transfer step of the serialization approach.

The state transfer overhead of a component depends on two factors. One is the number of fields the target component declares. The other is the complexity of each individual field.

That is, the state transfer time would be longer if a field refers to an object rather than a primitive type. Note that the total component number of the system does not affect the state transfer time of the component to be replaced, so it does not affect the reconfiguration time.

The fields declared by TCP1 are shown in Table 4-2. The fields of class PCB are also shown because it is an inner class of TCP1 and one PCB object is referred to by a field of TCP1.

The PCB class implements the protocol control block (PCB) of TCP.

The effect of preloading is shown in Table 4-3, indicating that the preloading technique can eliminate over 35% of the state transfer time. The preloading performance is measured on the first reconfiguration of the component framework’s lifetime because reconfiguration is not a very frequent event. However, if the serialization-only version performs a second

Table 4-3: Effect of the preloading technique.

Preloading

getrusage 128.27 80.75 62.95%

System.currentTimeMillis 201.76 130.73 64.79%

TCP1 PCB

Primitive Fields 5 24

Object Fields 2 6

Total 7 30

Table 4-2: The fields defined in the TCP1 and PCB classes.

reconfiguration, the performance will be close to that of the preloading version.

Although the preloading technique reduces the overhead caused by class loading, the serialization itself is still slow due to several reasons. Firstly, serialization is implemented as Java library classes instead of a built-in feature of the virtual machine. The price of portability is that it leads to additional bytecode execution time. Secondly, Java serialization stores the complete object graph to the byte stream. During deserialization, a new version of the complete object graph is constructed and is independent of the original object graph.

However, from the perspective of the component framework, the objects referred to by the old component can be simply attached to the new component, rather than being recreated.

4.4 Summary

In this chapter, a powerful, general-purpose, and performance-improved component framework for dynamic reconfiguration is proposed. The programming rules for the components are the same as those described in the previous chapter, but the implementation presented here differs from the implementation of the protocol framework in several aspects.

First, the general-purpose component framework adopts a new implementation approach based on JNI and JVMDI, which is six times faster than the protocol framework. The performance is considerably improved because the state transfer mechanism is implemented in C rather than in Java. Second, the technique of preserving the safe reconfiguration point is also different. The new implementation exploits JVMDI to inspect the thread stacks, and this technique does not need any synchronization mechanism such as a lock or a synchronization protocol. Third, the new component framework supports several update formats not handled in the protocol framework. The most notable one is multiple update, which can replace several components at one time. Next, the external interfaces are different. The protocol

framework connects to the socket library and network devices, but the general-purpose component framework does not have such a limitation. Then, the performance of the old implementation is also improved by using the preloading technique. Finally, the performance is measured more accurately by using a measurement function of the underlying operating system.

相關文件