The document discusses three puzzles related to OSGi concepts. The first puzzle involves determining which bundle fragments attach to host bundles based on their version ranges. The second puzzle involves a potential race condition between threads when using wait/notify to signal the availability of a service. The third puzzle involves determining what is printed by an activation method in a component implementation, based on the accessibility of the method and DS specification version. Each puzzle includes multiple choice answers and an explanation of the correct answer.
3. To what host(s) does fragment F attach when
resolved?
H1 H2
Bundle-SymbolicName: foo.host Bundle-SymbolicName: foo.host
Bundle-Version: 1.0 Bundle-Version: 2.0
F
Bundle-SymbolicName: foo.fragment
Fragment-Host: foo.host; version=”[1.0,2.0)”
(a) F attaches to only H1
(b) F attaches to only H2
(c) F attaches to both H1 and H2
(d) F does not attach to either H1 or H2
Tuesday, March 22, 2011
4. To what host(s) does fragment F attach when
resolved?
(a) F attaches to only H1
(b) F attaches to only H2
(c) F attaches to both H1 and H2
(d) F does not attach to either H1 or H2
bundle-version is the proper attribute! Note: in
4.3 attribute matching is now supported, so the
answer will be (d)!
Tuesday, March 22, 2011
6. 2. Waiting For Service
Thread 1
// a service in which the tracker is interested is registered
...
Waiter waiter;
public T addingService(ServiceReference<S> reference) {
synchronized (waiter) {
waiter.notify(); // tell waiter about the service
}
return super.addingService(reference);
}
Thread 2
// waiter object
ServiceTracker tracker;
void waitingForService {
synchronized (this) {
wait(); // waiting here for a service
}
T service = tracker.getService();
System.out.println(service);
}
Tuesday, March 22, 2011
7. What is printed by Thread 2?
Thread 1
// a service in which the tracker is interested is registered
...
Waiter waiter;
(a) nothing; thread
public T addingService(ServiceReference<S> reference) {
synchronized (waiter) { 2 does not reach
waiter.notify(); // tell waiter about the service
}
return super.addingService(reference);
println
}
(b) the service
Thread 2 object
// waiter object
ServiceTracker tracker; (c) null
(d) none of the
void waitingForService {
synchronized (this) {
wait(); // waiting here for a service
}
T service = tracker.getService();
above
System.out.println(service);
}
Tuesday, March 22, 2011
8. What is printed by Thread 2?
(a) nothing; thread 2 does not reach println
(b) the service object
(c) null
(d) none of the above: race condition
The answer can be (b) or (c) depending on how the
race works out.
Tuesday, March 22, 2011
9. Another Look
Thread 1
Waiter waiter;
public T addingService(ServiceReference<S> reference) {
synchronized (waiter) {
waiter.notify(); // tell waiter about the service
}
return super.addingService(reference);
// until this method returns, the tracker is not actually tracking the service!
}
Thread 2
// waiter object
ServiceTracker tracker;
void waitingForService {
synchronized (this) {
wait(); // waiting here for a service
}
T service = tracker.getService();
System.out.println(service);
}
Tuesday, March 22, 2011
10. 3. Activator
Component Description
<component name="example.activator">
<implementation class="com.acme.Activator"/>
</component>
Component Implementation
public class Activator {
private String data = null;
public Activator() {
data = “initialized”;
}
private void activate(ComponentContext context) {
System.out.println(data);
}
}
Tuesday, March 22, 2011
11. What is printed by the activate method?
Component Description
<component name="example.activator">
(a) null
<implementation class="com.acme.Activator"/>
</component>
(b) initialized
Component Implementation (c) throws
public class Activator { exception
private String data = null;
public Activator() {
data = “initialized”;
(d) none of the
}
private void activate(ComponentContext context) {
above
System.out.println(data);
}
}
Tuesday, March 22, 2011
12. What is printed by the activate method?
(a) null
(b) initialized
(c) throws exception
(d) none of the above: activate method is not
called
The component description does not specify a
namespace and thus is the DS 1.0 namespace. DS
1.0 required the activate method to be at least
protected!
Tuesday, March 22, 2011
13. One Solution: Change accessibility
Component Description
<component name="example.activator">
<implementation class="com.acme.Activator"/>
</component>
Component Implementation
public class Activator {
private String data = null;
public Activator() {
data = “initialized”;
}
protected void activate(ComponentContext context) {
System.out.println(data);
}
}
Tuesday, March 22, 2011
14. Better Solution: Specify the DS 1.1 namespace
Component Description
<scr:component name="example.activator"
xmlns:scr="http://www.osgi.org/xmlns/scr/v1.1.0">
<implementation class="com.acme.Activator"/>
</scr:component>
Component Implementation
public class Activator {
private String data = null;
public Activator() {
data = “initialized”;
}
private void activate(ComponentContext context) {
System.out.println(data);
}
}
Tuesday, March 22, 2011