Mir

Merge lp:~mir-team/mir/trunk-0.1.8 into lp:mir/0.1

Proposed by Daniel van Vugt on 2014-04-02
Status: Merged
Merged at revision: 1183
Proposed branch: lp:~mir-team/mir/trunk-0.1.8
Merge into: lp:mir/0.1
Diff against target: 16448 lines (+6002/-3362)
277 files modified
3rd_party/android-input/android/CMakeLists.txt (+2/-0)
3rd_party/android-input/android/frameworks/base/services/input/EventHub.cpp (+46/-92)
3rd_party/android-input/android/frameworks/base/services/input/EventHub.h (+6/-5)
CMakeLists.txt (+1/-1)
benchmarks/android-input/CMakeLists.txt (+3/-1)
cmake/MirCommon.cmake (+15/-4)
cmake/src/mir/CMakeLists.txt (+5/-0)
cmake/src/mir/fail_on_success.sh (+8/-0)
cmake/src/mir/mir_discover_gtest_tests.cpp (+15/-2)
debian/changelog (+66/-0)
debian/control (+3/-3)
debian/libmirserver18.install (+1/-1)
deploy-and-test.sh (+21/-0)
examples/demo-shell/demo_renderer.cpp (+271/-0)
examples/demo-shell/demo_renderer.h (+15/-0)
examples/render_overlays.cpp (+9/-7)
examples/render_surfaces.cpp (+19/-7)
include/platform/mir/graphics/display_buffer.h (+2/-3)
include/platform/mir/graphics/gl_config.h (+54/-0)
include/platform/mir/graphics/platform.h (+8/-1)
include/platform/mir/graphics/renderable.h (+20/-13)
include/platform/mir/options/default_configuration.h (+1/-0)
include/platform/mir/shared_library_loader.h (+28/-0)
include/server/mir/compositor/buffer_stream.h (+1/-1)
include/server/mir/compositor/gl_renderer.h (+27/-4)
include/server/mir/compositor/renderer.h (+2/-2)
include/server/mir/compositor/scene.h (+7/-4)
include/server/mir/default_server_configuration.h (+12/-8)
include/server/mir/frontend/display_changer.h (+0/-1)
include/server/mir/frontend/session_authorizer.h (+3/-1)
include/server/mir/input/surface.h (+1/-1)
include/server/mir/scene/surface.h (+59/-0)
include/server/mir/scene/surface_configurator.h (+4/-4)
include/server/mir/scene/surface_coordinator.h (+17/-12)
include/server/mir/scene/surface_event_source.h (+49/-0)
include/server/mir/scene/surface_factory.h (+14/-14)
include/server/mir/scene/surface_observer.h (+45/-0)
include/server/mir/scene/surface_ranker.h (+2/-2)
include/server/mir/shell/surface.h (+1/-3)
include/server/mir/shell/surface_factory.h (+6/-8)
include/shared/mir/geometry/length.h (+102/-0)
include/test/mir_test_doubles/fake_renderable.h (+5/-5)
include/test/mir_test_doubles/mock_buffer_bundle.h (+1/-1)
include/test/mir_test_doubles/mock_buffer_stream.h (+1/-1)
include/test/mir_test_doubles/mock_display_buffer.h (+1/-1)
include/test/mir_test_doubles/mock_display_changer.h (+0/-1)
include/test/mir_test_doubles/mock_display_device.h (+1/-1)
include/test/mir_test_doubles/mock_egl.h (+27/-0)
include/test/mir_test_doubles/mock_gl_config.h (+43/-0)
include/test/mir_test_doubles/mock_hwc_composer_device_1.h (+0/-105)
include/test/mir_test_doubles/mock_hwc_device_wrapper.h (+42/-0)
include/test/mir_test_doubles/mock_input_surface.h (+2/-2)
include/test/mir_test_doubles/mock_renderable.h (+12/-3)
include/test/mir_test_doubles/mock_scene.h (+6/-2)
include/test/mir_test_doubles/mock_surface.h (+14/-12)
include/test/mir_test_doubles/mock_surface_configurator.h (+4/-4)
include/test/mir_test_doubles/mock_surface_factory.h (+4/-3)
include/test/mir_test_doubles/mock_surface_ranker.h (+2/-2)
include/test/mir_test_doubles/null_display_buffer.h (+1/-1)
include/test/mir_test_doubles/null_display_changer.h (+0/-3)
include/test/mir_test_doubles/null_platform.h (+2/-1)
include/test/mir_test_doubles/null_surface_configurator.h (+4/-4)
include/test/mir_test_doubles/stub_buffer_stream.h (+1/-1)
include/test/mir_test_doubles/stub_display_builder.h (+1/-1)
include/test/mir_test_doubles/stub_display_device.h (+1/-1)
include/test/mir_test_doubles/stub_gl_config.h (+43/-0)
include/test/mir_test_doubles/stub_ipc_factory.h (+1/-1)
include/test/mir_test_doubles/stub_renderable.h (+2/-2)
include/test/mir_test_doubles/stub_session_authorizer.h (+4/-0)
include/test/mir_test_doubles/stub_surface_builder.h (+0/-69)
include/test/mir_test_doubles/stub_surface_ranker.h (+0/-44)
include/test/mir_test_framework/declarative_placement_strategy.h (+64/-0)
include/test/mir_test_framework/udev_environment.h (+1/-0)
src/client/default_connection_configuration.cpp (+1/-1)
src/client/lttng/input_receiver_report_tp.h (+1/-0)
src/client/lttng/rpc_report_tp.h (+1/-0)
src/client/mir_client_library.cpp (+11/-2)
src/client/rpc/mir_basic_rpc_channel.cpp (+3/-3)
src/client/rpc/mir_basic_rpc_channel.h (+4/-3)
src/client/rpc/mir_socket_rpc_channel.cpp (+41/-32)
src/client/rpc/mir_socket_rpc_channel.h (+3/-1)
src/platform/CMakeLists.txt (+2/-1)
src/platform/graphics/android/CMakeLists.txt (+4/-0)
src/platform/graphics/android/android_display.cpp (+2/-1)
src/platform/graphics/android/android_display.h (+2/-0)
src/platform/graphics/android/android_platform.cpp (+37/-4)
src/platform/graphics/android/android_platform.h (+2/-1)
src/platform/graphics/android/display_buffer.cpp (+1/-1)
src/platform/graphics/android/display_buffer.h (+1/-1)
src/platform/graphics/android/display_device.h (+1/-1)
src/platform/graphics/android/fb_device.cpp (+1/-1)
src/platform/graphics/android/fb_device.h (+1/-1)
src/platform/graphics/android/gl_context.cpp (+17/-10)
src/platform/graphics/android/gl_context.h (+4/-1)
src/platform/graphics/android/hwc_common_device.cpp (+2/-2)
src/platform/graphics/android/hwc_common_device.h (+2/-1)
src/platform/graphics/android/hwc_device.cpp (+2/-1)
src/platform/graphics/android/hwc_device.h (+2/-15)
src/platform/graphics/android/hwc_fb_device.cpp (+12/-17)
src/platform/graphics/android/hwc_fb_device.h (+5/-1)
src/platform/graphics/android/hwc_formatted_logger.cpp (+177/-0)
src/platform/graphics/android/hwc_formatted_logger.h (+41/-0)
src/platform/graphics/android/hwc_layerlist.cpp (+4/-4)
src/platform/graphics/android/hwc_layerlist.h (+2/-2)
src/platform/graphics/android/hwc_logger.h (+46/-0)
src/platform/graphics/android/hwc_wrapper.h (+47/-0)
src/platform/graphics/android/real_hwc_wrapper.cpp (+11/-2)
src/platform/graphics/android/real_hwc_wrapper.h (+6/-3)
src/platform/graphics/android/resource_factory.cpp (+35/-2)
src/platform/graphics/android/resource_factory.h (+4/-0)
src/platform/graphics/mesa/CMakeLists.txt (+1/-0)
src/platform/graphics/mesa/display.cpp (+13/-3)
src/platform/graphics/mesa/display.h (+5/-2)
src/platform/graphics/mesa/display_buffer.cpp (+3/-1)
src/platform/graphics/mesa/display_buffer.h (+3/-1)
src/platform/graphics/mesa/display_helpers.cpp (+15/-3)
src/platform/graphics/mesa/display_helpers.h (+5/-5)
src/platform/graphics/mesa/platform.cpp (+11/-1)
src/platform/graphics/mesa/platform.h (+2/-1)
src/platform/options/default_configuration.cpp (+32/-3)
src/platform/shared_library_loader.cpp (+38/-0)
src/server/CMakeLists.txt (+1/-1)
src/server/compositor/buffer_bundle.h (+13/-1)
src/server/compositor/buffer_stream_surfaces.cpp (+2/-2)
src/server/compositor/buffer_stream_surfaces.h (+1/-1)
src/server/compositor/bypass.cpp (+6/-1)
src/server/compositor/default_display_buffer_compositor.cpp (+32/-57)
src/server/compositor/default_display_buffer_compositor.h (+1/-2)
src/server/compositor/gl_renderer.cpp (+68/-22)
src/server/compositor/occlusion.cpp (+28/-16)
src/server/compositor/occlusion.h (+2/-24)
src/server/compositor/rendering_operator.cpp (+5/-11)
src/server/compositor/rendering_operator.h (+3/-7)
src/server/compositor/screencast_display_buffer.cpp (+1/-1)
src/server/compositor/screencast_display_buffer.h (+1/-1)
src/server/compositor/switching_bundle.cpp (+6/-3)
src/server/compositor/switching_bundle.h (+3/-4)
src/server/compositor/temporary_buffers.cpp (+2/-2)
src/server/compositor/temporary_buffers.h (+1/-1)
src/server/default_server_configuration.cpp (+11/-6)
src/server/frontend/CMakeLists.txt (+1/-0)
src/server/frontend/default_configuration.cpp (+23/-7)
src/server/frontend/event_sender.cpp (+1/-1)
src/server/frontend/message_receiver.h (+3/-1)
src/server/frontend/message_sender.h (+2/-2)
src/server/frontend/protobuf_ipc_factory.h (+1/-2)
src/server/frontend/protobuf_responder.cpp (+9/-8)
src/server/frontend/protobuf_responder.h (+1/-1)
src/server/frontend/protobuf_session_creator.cpp (+1/-2)
src/server/frontend/session_mediator.cpp (+0/-6)
src/server/frontend/socket_messenger.cpp (+29/-14)
src/server/frontend/socket_messenger.h (+4/-3)
src/server/frontend/socket_session.cpp (+16/-9)
src/server/frontend/socket_session.h (+3/-2)
src/server/frontend/unauthorized_display_changer.cpp (+0/-5)
src/server/frontend/unauthorized_display_changer.h (+0/-2)
src/server/frontend/unauthorized_screencast.cpp (+46/-0)
src/server/frontend/unauthorized_screencast.h (+44/-0)
src/server/graphics/default_configuration.cpp (+20/-21)
src/server/graphics/nested/nested_display.cpp (+11/-4)
src/server/graphics/nested/nested_display.h (+6/-2)
src/server/graphics/nested/nested_output.cpp (+1/-1)
src/server/graphics/nested/nested_output.h (+1/-1)
src/server/graphics/nested/nested_platform.cpp (+5/-2)
src/server/graphics/nested/nested_platform.h (+2/-1)
src/server/graphics/offscreen/display_buffer.cpp (+1/-1)
src/server/graphics/offscreen/display_buffer.h (+1/-1)
src/server/mirserver.pc.in (+1/-1)
src/server/scene/CMakeLists.txt (+1/-2)
src/server/scene/application_session.cpp (+10/-2)
src/server/scene/basic_surface.cpp (+193/-27)
src/server/scene/basic_surface.h (+73/-26)
src/server/scene/default_configuration.cpp (+18/-27)
src/server/scene/gl_pixel_buffer.cpp (+7/-0)
src/server/scene/mediating_display_changer.cpp (+0/-23)
src/server/scene/mediating_display_changer.h (+0/-2)
src/server/scene/mutable_surface_state.h (+0/-52)
src/server/scene/surface_allocator.cpp (+8/-4)
src/server/scene/surface_allocator.h (+8/-4)
src/server/scene/surface_controller.cpp (+23/-13)
src/server/scene/surface_controller.h (+16/-15)
src/server/scene/surface_event_source.cpp (+62/-0)
src/server/scene/surface_impl.cpp (+0/-273)
src/server/scene/surface_impl.h (+0/-114)
src/server/scene/surface_source.cpp (+0/-47)
src/server/scene/surface_source.h (+0/-64)
src/server/scene/surface_stack.cpp (+23/-34)
src/server/scene/surface_stack.h (+19/-19)
src/server/scene/surface_stack_model.h (+13/-6)
src/server/shell/default_configuration.cpp (+1/-1)
src/server/shell/default_focus_mechanism.cpp (+3/-1)
src/server/shell/organising_surface_factory.cpp (+29/-10)
src/server/shell/organising_surface_factory.h (+9/-6)
src/shared/sharedlibrary/CMakeLists.txt (+5/-0)
tests/CMakeLists.txt (+3/-10)
tests/acceptance-tests/test_client_authorization.cpp (+3/-0)
tests/acceptance-tests/test_client_input.cpp (+33/-70)
tests/acceptance-tests/test_client_screencast.cpp (+50/-0)
tests/acceptance-tests/test_display_configuration.cpp (+5/-4)
tests/acceptance-tests/test_protobuf.cpp (+5/-0)
tests/acceptance-tests/test_server_disconnect.cpp (+2/-0)
tests/acceptance-tests/test_shell_control_of_surface_configuration.cpp (+6/-6)
tests/acceptance-tests/test_surfaces_with_output_id.cpp (+7/-1)
tests/integration-tests/compositor/test_buffer_stream.cpp (+21/-21)
tests/integration-tests/compositor/test_swapping_swappers.cpp (+2/-4)
tests/integration-tests/graphics/android/test_display_integration.cpp (+9/-6)
tests/integration-tests/graphics/android/test_internal_client.cpp (+7/-7)
tests/integration-tests/graphics/mesa/test_buffer_integration.cpp (+4/-1)
tests/integration-tests/test_display_info.cpp (+2/-1)
tests/integration-tests/test_session_manager.cpp (+1/-1)
tests/integration-tests/test_surfaceloop.cpp (+4/-2)
tests/integration-tests/test_swapinterval.cpp (+1/-1)
tests/mir_test_framework/CMakeLists.txt (+10/-11)
tests/mir_test_framework/declarative_placement_strategy.cpp (+58/-0)
tests/mir_test_framework/stubbed_server_configuration.cpp (+2/-1)
tests/mir_test_framework/udev_environment.cpp (+22/-2)
tests/mir_test_framework/udev_recordings/bluetooth-magic-trackpad.ioctl (+21/-0)
tests/mir_test_framework/udev_recordings/bluetooth-magic-trackpad.umockdev (+222/-0)
tests/mir_test_framework/udev_recordings/laptop-keyboard.ioctl (+12/-0)
tests/mir_test_framework/udev_recordings/laptop-keyboard.umockdev (+74/-0)
tests/mir_test_framework/udev_recordings/synaptics-touchpad.ioctl (+29/-0)
tests/mir_test_framework/udev_recordings/synaptics-touchpad.umockdev (+65/-0)
tests/mir_test_framework/udev_recordings/usb-keyboard.ioctl (+13/-0)
tests/mir_test_framework/udev_recordings/usb-keyboard.umockdev (+244/-0)
tests/mir_test_framework/udev_recordings/usb-mouse.ioctl (+14/-0)
tests/mir_test_framework/udev_recordings/usb-mouse.umockdev (+240/-0)
tests/mir_test_framework/using_stub_client_platform.cpp (+11/-2)
tests/unit-tests/CMakeLists.txt (+5/-14)
tests/unit-tests/android_input/CMakeLists.txt (+1/-0)
tests/unit-tests/android_input/test_eventhub.cpp (+125/-0)
tests/unit-tests/client/test_mir_connection.cpp (+6/-0)
tests/unit-tests/compositor/test_default_display_buffer_compositor.cpp (+348/-444)
tests/unit-tests/compositor/test_gl_renderer.cpp (+21/-2)
tests/unit-tests/compositor/test_multi_threaded_compositor.cpp (+5/-2)
tests/unit-tests/compositor/test_occlusion.cpp (+123/-81)
tests/unit-tests/compositor/test_rendering_operator.cpp (+15/-15)
tests/unit-tests/compositor/test_switching_bundle.cpp (+69/-51)
tests/unit-tests/frontend/test_event_sender.cpp (+7/-7)
tests/unit-tests/frontend/test_session_mediator.cpp (+4/-5)
tests/unit-tests/frontend/test_socket_session.cpp (+43/-14)
tests/unit-tests/geometry/CMakeLists.txt (+1/-0)
tests/unit-tests/geometry/test-length.cpp (+124/-0)
tests/unit-tests/graphics/android/CMakeLists.txt (+1/-0)
tests/unit-tests/graphics/android/hwc_struct_helpers.h (+8/-0)
tests/unit-tests/graphics/android/test_android_fb.cpp (+64/-31)
tests/unit-tests/graphics/android/test_hwc_common_device.cpp (+3/-1)
tests/unit-tests/graphics/android/test_hwc_device.cpp (+5/-9)
tests/unit-tests/graphics/android/test_hwc_display.cpp (+6/-1)
tests/unit-tests/graphics/android/test_hwc_fb_device.cpp (+44/-74)
tests/unit-tests/graphics/android/test_hwc_logger.cpp (+132/-0)
tests/unit-tests/graphics/android/test_hwc_wrapper.cpp (+28/-7)
tests/unit-tests/graphics/android/test_output_builder.cpp (+4/-1)
tests/unit-tests/graphics/android/test_resource_factory.cpp (+5/-4)
tests/unit-tests/graphics/mesa/test_display.cpp (+41/-8)
tests/unit-tests/graphics/mesa/test_display_buffer.cpp (+12/-0)
tests/unit-tests/graphics/mesa/test_display_configuration.cpp (+4/-2)
tests/unit-tests/graphics/mesa/test_display_multi_monitor.cpp (+7/-4)
tests/unit-tests/graphics/mesa/test_internal_native_display.cpp (+0/-4)
tests/unit-tests/graphics/mesa/test_internal_native_surface.cpp (+0/-3)
tests/unit-tests/graphics/nested/CMakeLists.txt (+1/-0)
tests/unit-tests/graphics/nested/test_nested_display.cpp (+27/-0)
tests/unit-tests/graphics/test_display.cpp (+4/-2)
tests/unit-tests/input/android/test_android_input_application_handle.cpp (+1/-1)
tests/unit-tests/input/android/test_android_input_registrar.cpp (+2/-3)
tests/unit-tests/input/android/test_android_input_window_handle.cpp (+18/-11)
tests/unit-tests/scene/test_application_session.cpp (+12/-14)
tests/unit-tests/scene/test_basic_surface.cpp (+124/-106)
tests/unit-tests/scene/test_default_focus_mechanism.cpp (+23/-40)
tests/unit-tests/scene/test_gl_pixel_buffer.cpp (+10/-0)
tests/unit-tests/scene/test_session_manager.cpp (+19/-17)
tests/unit-tests/scene/test_surface.cpp (+73/-31)
tests/unit-tests/scene/test_surface_controller.cpp (+36/-14)
tests/unit-tests/scene/test_surface_impl.cpp (+117/-209)
tests/unit-tests/scene/test_surface_stack.cpp (+143/-317)
tests/unit-tests/shell/test_organising_surface_factory.cpp (+24/-16)
tools/valgrind_suppressions_armhf (+30/-0)
tools/valgrind_suppressions_generic (+7/-0)
To merge this branch: bzr merge lp:~mir-team/mir/trunk-0.1.8
Reviewer Review Type Date Requested Status
PS Jenkins bot (community) continuous-integration Approve on 2014-04-07
Daniel van Vugt Approve on 2014-04-07
kevin gunn (community) 2014-04-02 Approve on 2014-04-07
Review via email: mp+213790@code.launchpad.net

Commit message

New upstream Mir release 0.1.8 (development-branch r1523), plus changelog
additions.

To post a comment you must log in.
Daniel van Vugt (vanvugt) wrote :

There is arguably one important fix missing from the 0.1.8 release. That is bug 1301040. We might want to add it in here...

Kevin DuBois (kdub) wrote :

Yes, the fix for that lp:~mterry/mir/missing-links (in the landing queue at time of this comment) should make it into this release. (would be caught during the silo build)

lp:~mir-team/mir/trunk-0.1.8 updated on 2014-04-04
1185. By Daniel van Vugt on 2014-04-04

Merge mterry's fix for LP: #1301040

kevin gunn (kgunn72) wrote :

there is one more we should cherry pick for https://bugs.launchpad.net/mir/+bug/1256360
which is proposed to be solved by https://code.launchpad.net/~albaguirre/mir/fix-1256360/+merge/214355

review: Needs Fixing
lp:~mir-team/mir/trunk-0.1.8 updated on 2014-04-07
1186. By Daniel van Vugt on 2014-04-07

Merge Alberto's fix for LP: #1256360.

kevin gunn (kgunn72) wrote :

Did you test your feature/code change/bug fix ? what device(s) ?
yes - n4, desktop

Did you break mir server API or ABI and have the relevant bumps to .so and debian docs been made ?
yes, server ABI only, bumps have been made

Did you break mir client API or ABI and have you followed up with the known clients & announced on mir-devel mailing list ?
yes, server only, unity-mir/server updates made

review: Approve
Daniel van Vugt (vanvugt) wrote :

Changelog entry missing for latest commit.

review: Needs Fixing
lp:~mir-team/mir/trunk-0.1.8 updated on 2014-04-07
1187. By Daniel van Vugt on 2014-04-07

Remember to mention that last cherrypick in changelog

Daniel van Vugt (vanvugt) :
review: Approve

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1=== modified file '3rd_party/android-input/android/CMakeLists.txt'
2--- 3rd_party/android-input/android/CMakeLists.txt 2014-03-06 06:05:17 +0000
3+++ 3rd_party/android-input/android/CMakeLists.txt 2014-04-07 13:29:13 +0000
4@@ -7,6 +7,7 @@
5 system/extras/ext4_utils
6
7 ${PROJECT_SOURCE_DIR}/include/server
8+ ${PROJECT_SOURCE_DIR}/include/platform
9 )
10
11 add_definitions(
12@@ -64,6 +65,7 @@
13 target_link_libraries(
14 android-input
15
16+ mirplatform
17 ${Boost_LIBRARIES}
18 )
19
20
21=== modified file '3rd_party/android-input/android/frameworks/base/services/input/EventHub.cpp'
22--- 3rd_party/android-input/android/frameworks/base/services/input/EventHub.cpp 2013-10-03 05:12:59 +0000
23+++ 3rd_party/android-input/android/frameworks/base/services/input/EventHub.cpp 2014-04-07 13:29:13 +0000
24@@ -205,34 +205,34 @@
25
26 // --- EventHub ---
27
28-const uint32_t EventHub::EPOLL_ID_INOTIFY;
29+const uint32_t EventHub::EPOLL_ID_UDEV;
30 const uint32_t EventHub::EPOLL_ID_WAKE;
31 const int EventHub::EPOLL_SIZE_HINT;
32 const int EventHub::EPOLL_MAX_EVENTS;
33
34 EventHub::EventHub(std::shared_ptr<mi::InputReport> const& input_report) :
35 input_report(input_report),
36+ device_listener{mir::udev::Context()},
37 mBuiltInKeyboardId(NO_BUILT_IN_KEYBOARD), mNextDeviceId(1),
38 mOpeningDevices(0), mClosingDevices(0),
39 mNeedToSendFinishedDeviceScan(false),
40 mNeedToReopenDevices(false), mNeedToScanDevices(true),
41- mPendingEventCount(0), mPendingEventIndex(0), mPendingINotify(false) {
42+ mPendingEventCount(0), mPendingEventIndex(0), mPendingUdevEvent(false) {
43 acquire_wake_lock(PARTIAL_WAKE_LOCK, WAKE_LOCK_ID);
44
45 mEpollFd = epoll_create(EPOLL_SIZE_HINT);
46 LOG_ALWAYS_FATAL_IF(mEpollFd < 0, "Could not create epoll instance. errno=%d", errno);
47
48- mINotifyFd = inotify_init();
49- int result = inotify_add_watch(mINotifyFd, DEVICE_PATH, IN_DELETE | IN_CREATE | IN_ATTRIB);
50- LOG_ALWAYS_FATAL_IF(result < 0, "Could not register INotify for %s. errno=%d",
51- DEVICE_PATH, errno);
52+ device_listener.filter_by_subsystem("input");
53+ device_listener.enable();
54+
55
56 struct epoll_event eventItem;
57 memset(&eventItem, 0, sizeof(eventItem));
58 eventItem.events = EPOLLIN;
59- eventItem.data.u32 = EPOLL_ID_INOTIFY;
60- result = epoll_ctl(mEpollFd, EPOLL_CTL_ADD, mINotifyFd, &eventItem);
61- LOG_ALWAYS_FATAL_IF(result != 0, "Could not add INotify to epoll instance. errno=%d", errno);
62+ eventItem.data.u32 = EPOLL_ID_UDEV;
63+ int result = epoll_ctl(mEpollFd, EPOLL_CTL_ADD, device_listener.fd(), &eventItem);
64+ LOG_ALWAYS_FATAL_IF(result != 0, "Could not add Udev monitor to epoll instance. errno=%d", errno);
65
66 int wakeFds[2];
67 result = pipe(wakeFds);
68@@ -265,7 +265,6 @@
69 }
70
71 ::close(mEpollFd);
72- ::close(mINotifyFd);
73 ::close(mWakeReadPipeFd);
74 ::close(mWakeWritePipeFd);
75
76@@ -730,9 +729,9 @@
77 bool deviceChanged = false;
78 while (mPendingEventIndex < mPendingEventCount) {
79 const struct epoll_event& eventItem = mPendingEventItems[mPendingEventIndex++];
80- if (eventItem.data.u32 == EPOLL_ID_INOTIFY) {
81+ if (eventItem.data.u32 == EPOLL_ID_UDEV) {
82 if (eventItem.events & EPOLLIN) {
83- mPendingINotify = true;
84+ mPendingUdevEvent = true;
85 } else {
86 ALOGW("Received unexpected epoll event 0x%08x for INotify.", eventItem.events);
87 }
88@@ -839,9 +838,9 @@
89 // readNotify() will modify the list of devices so this must be done after
90 // processing all other events to ensure that we read all remaining events
91 // before closing the devices.
92- if (mPendingINotify && mPendingEventIndex >= mPendingEventCount) {
93- mPendingINotify = false;
94- readNotifyLocked();
95+ if (mPendingUdevEvent && mPendingEventIndex >= mPendingEventCount) {
96+ mPendingUdevEvent = false;
97+ handleUdevEventsLocked();
98 deviceChanged = true;
99 }
100
101@@ -916,15 +915,44 @@
102 }
103
104 void EventHub::scanDevicesLocked() {
105- status_t res = scanDirLocked(DEVICE_PATH);
106- if(res < 0) {
107- ALOGE("scan dir failed for %s\n", DEVICE_PATH);
108+ mir::udev::Enumerator input_enumerator{std::make_shared<mir::udev::Context>()};
109+
110+ input_enumerator.match_subsystem("input");
111+ input_enumerator.scan_devices();
112+
113+ for (auto& device : input_enumerator)
114+ {
115+ if (device.devnode() != nullptr)
116+ {
117+ openDeviceLocked(device.devnode());
118+ }
119 }
120+
121 if (mDevices.indexOfKey(VIRTUAL_KEYBOARD_ID) < 0) {
122 createVirtualKeyboardLocked();
123 }
124 }
125
126+void EventHub::handleUdevEventsLocked()
127+{
128+ device_listener.process_events([this](mir::udev::Monitor::EventType type, mir::udev::Device const& dev){
129+ if (type == mir::udev::Monitor::ADDED)
130+ {
131+ if (dev.devnode() != nullptr)
132+ {
133+ openDeviceLocked(dev.devnode());
134+ }
135+ }
136+ else if (type == mir::udev::Monitor::REMOVED)
137+ {
138+ if (dev.devnode() != nullptr)
139+ {
140+ closeDeviceByPathLocked(dev.devnode());
141+ }
142+ }
143+ });
144+}
145+
146 // ----------------------------------------------------------------------------
147
148 static bool containsNonZeroByte(const uint8_t* array, uint32_t startIndex, uint32_t endIndex) {
149@@ -1391,80 +1419,6 @@
150 }
151 }
152
153-status_t EventHub::readNotifyLocked() {
154- int res;
155- char devname[PATH_MAX];
156- char *filename;
157- char event_buf[512];
158- int event_size;
159- int event_pos = 0;
160- struct inotify_event *event;
161-
162- ALOGV("EventHub::readNotify nfd: %d\n", mINotifyFd);
163- res = read(mINotifyFd, event_buf, sizeof(event_buf));
164- if(res < (int)sizeof(*event)) {
165- if(errno == EINTR)
166- return 0;
167- ALOGW("could not get event, %s\n", strerror(errno));
168- return -1;
169- }
170- //printf("got %d bytes of event information\n", res);
171-
172- strcpy(devname, DEVICE_PATH);
173- filename = devname + strlen(devname);
174- *filename++ = '/';
175-
176- while(res >= (int)sizeof(*event)) {
177- event = (struct inotify_event *)(event_buf + event_pos);
178- //printf("%d: %08x \"%s\"\n", event->wd, event->mask, event->len ? event->name : "");
179- if(event->len) {
180- strcpy(filename, event->name);
181- if(event->mask & IN_CREATE) {
182- openDeviceLocked(devname);
183- } else if (event->mask & IN_ATTRIB) {
184- Device* device = getDeviceByPathLocked(devname);
185- if (!device) {
186- ALOGI("Retry opening device file %s", devname);
187- // file permissions might have changed, making the device readable now
188- // let's retry opening it
189- openDeviceLocked(devname);
190- }
191- } else {
192- ALOGI("Removing device '%s' due to inotify event\n", devname);
193- closeDeviceByPathLocked(devname);
194- }
195- }
196- event_size = sizeof(*event) + event->len;
197- res -= event_size;
198- event_pos += event_size;
199- }
200- return 0;
201-}
202-
203-status_t EventHub::scanDirLocked(const char *dirname)
204-{
205- char devname[PATH_MAX];
206- char *filename;
207- DIR *dir;
208- struct dirent *de;
209- dir = opendir(dirname);
210- if(dir == NULL)
211- return -1;
212- strcpy(devname, dirname);
213- filename = devname + strlen(devname);
214- *filename++ = '/';
215- while((de = readdir(dir))) {
216- if(de->d_name[0] == '.' &&
217- (de->d_name[1] == '\0' ||
218- (de->d_name[1] == '.' && de->d_name[2] == '\0')))
219- continue;
220- strcpy(filename, de->d_name);
221- openDeviceLocked(devname);
222- }
223- closedir(dir);
224- return 0;
225-}
226-
227 void EventHub::requestReopenDevices() {
228 ALOGV("requestReopenDevices() called");
229
230
231=== modified file '3rd_party/android-input/android/frameworks/base/services/input/EventHub.h'
232--- 3rd_party/android-input/android/frameworks/base/services/input/EventHub.h 2013-10-03 05:12:59 +0000
233+++ 3rd_party/android-input/android/frameworks/base/services/input/EventHub.h 2014-04-07 13:29:13 +0000
234@@ -18,6 +18,8 @@
235 #ifndef _RUNTIME_EVENT_HUB_H
236 #define _RUNTIME_EVENT_HUB_H
237
238+#include "mir/udev/wrapper.h"
239+
240 #include <androidfw/Input.h>
241 #include <androidfw/InputDevice.h>
242 #include <androidfw/Keyboard.h>
243@@ -366,9 +368,8 @@
244 void closeDeviceLocked(Device* device);
245 void closeAllDevicesLocked();
246
247- status_t scanDirLocked(const char *dirname);
248 void scanDevicesLocked();
249- status_t readNotifyLocked();
250+ void handleUdevEventsLocked();
251
252 Device* getDeviceLocked(int32_t deviceId) const;
253 Device* getDeviceByPathLocked(const char* devicePath) const;
254@@ -407,12 +408,12 @@
255 Vector<String8> mExcludedDevices;
256
257 int mEpollFd;
258- int mINotifyFd;
259+ mir::udev::Monitor device_listener;
260 int mWakeReadPipeFd;
261 int mWakeWritePipeFd;
262
263 // Ids used for epoll notifications not associated with devices.
264- static const uint32_t EPOLL_ID_INOTIFY = 0x80000001;
265+ static const uint32_t EPOLL_ID_UDEV = 0x80000001;
266 static const uint32_t EPOLL_ID_WAKE = 0x80000002;
267
268 // Epoll FD list size hint.
269@@ -425,7 +426,7 @@
270 struct epoll_event mPendingEventItems[EPOLL_MAX_EVENTS];
271 size_t mPendingEventCount;
272 size_t mPendingEventIndex;
273- bool mPendingINotify;
274+ bool mPendingUdevEvent;
275 };
276
277 // Made available to test
278
279=== modified file 'CMakeLists.txt'
280--- CMakeLists.txt 2014-03-06 06:05:17 +0000
281+++ CMakeLists.txt 2014-04-07 13:29:13 +0000
282@@ -28,7 +28,7 @@
283
284 set(MIR_VERSION_MAJOR 0)
285 set(MIR_VERSION_MINOR 1)
286-set(MIR_VERSION_PATCH 7)
287+set(MIR_VERSION_PATCH 8)
288
289 set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} ${CMAKE_CURRENT_SOURCE_DIR}/cmake)
290 execute_process(
291
292=== modified file 'benchmarks/android-input/CMakeLists.txt'
293--- benchmarks/android-input/CMakeLists.txt 2013-10-15 10:10:05 +0000
294+++ benchmarks/android-input/CMakeLists.txt 2014-04-07 13:29:13 +0000
295@@ -5,7 +5,9 @@
296 )
297
298 include_directories(
299- ${Mir_SOURCE_DIR}/include/test)
300+ ${Mir_SOURCE_DIR}/include/test
301+ ${Mir_SOURCE_DIR}/include/platform
302+)
303
304 add_executable(input-reader-perf ${SOURCES})
305
306
307=== modified file 'cmake/MirCommon.cmake'
308--- cmake/MirCommon.cmake 2014-03-06 06:05:17 +0000
309+++ cmake/MirCommon.cmake 2014-04-07 13:29:13 +0000
310@@ -22,8 +22,10 @@
311 valgrind)
312
313 if(VALGRIND_EXECUTABLE)
314- set(VALGRIND_ARGS "--error-exitcode=1" "--trace-children=yes")
315+ set(VALGRIND_ARGS "--error-exitcode=1" "--trace-children=yes" "--leak-check=full" "--show-leak-kinds=definite" "--errors-for-leak-kinds=definite")
316+ set(VALGRIND_ARGS ${VALGRIND_ARGS} "--suppressions=${CMAKE_SOURCE_DIR}/tools/valgrind_suppressions_generic")
317 set(DISCOVER_FLAGS "--enable-memcheck")
318+ set(DISCOVER_FLAGS ${DISCOVER_FLAGS} "--suppressions=${CMAKE_SOURCE_DIR}/tools/valgrind_suppressions_generic")
319 if (TARGET_ARCH STREQUAL "arm-linux-gnueabihf")
320 set(VALGRIND_ARGS ${VALGRIND_ARGS} "--suppressions=${CMAKE_SOURCE_DIR}/tools/valgrind_suppressions_armhf")
321 set(DISCOVER_FLAGS ${DISCOVER_FLAGS} "--suppressions=${CMAKE_SOURCE_DIR}/tools/valgrind_suppressions_armhf")
322@@ -35,10 +37,11 @@
323
324 function (mir_discover_tests EXECUTABLE)
325 if(DISABLE_GTEST_TEST_DISCOVERY)
326- add_test(${EXECUTABLE} ${VALGRIND_EXECUTABLE} ${VALGRIND_ARGS} "${EXECUTABLE_OUTPUT_PATH}/${EXECUTABLE}")
327-
328+ add_test(${EXECUTABLE} ${VALGRIND_EXECUTABLE} ${VALGRIND_ARGS} ${EXECUTABLE_OUTPUT_PATH}/${EXECUTABLE} "--gtest_filter=-*DeathTest.*")
329+ add_test(${EXECUTABLE}_death_tests ${EXECUTABLE_OUTPUT_PATH}/${EXECUTABLE} "--gtest_filter=*DeathTest.*")
330 if (${ARGC} GREATER 1)
331 set_property(TEST ${EXECUTABLE} PROPERTY ENVIRONMENT ${ARGN})
332+ set_property(TEST ${EXECUTABLE}_death_tests PROPERTY ENVIRONMENT ${ARGN})
333 endif()
334 else()
335 set(CHECK_TEST_DISCOVERY_TARGET_NAME "check_discover_tests_in_${EXECUTABLE}")
336@@ -82,7 +85,15 @@
337 function (mir_add_memcheck_test)
338 if (ENABLE_MEMCHECK_OPTION)
339 if(DISABLE_GTEST_TEST_DISCOVERY)
340- ADD_TEST("memcheck-test" "sh" "-c" "${VALGRIND_EXECUTABLE} ${VALGRIND_ARGS} ${CMAKE_BINARY_DIR}/mir_gtest/mir_test_memory_error; if [ $? != 0 ]; then exit 0; else exit 1; fi")
341+ add_custom_target(
342+ memcheck_test ALL
343+ )
344+ ADD_TEST("memcheck-test" ${CMAKE_BINARY_DIR}/mir_gtest/fail_on_success.sh ${VALGRIND_EXECUTABLE} ${VALGRIND_ARGS} ${CMAKE_BINARY_DIR}/mir_gtest/mir_test_memory_error)
345+ add_dependencies(
346+ memcheck_test
347+
348+ mir_test_memory_error
349+ )
350 else()
351 add_custom_target(
352 memcheck_test ALL
353
354=== modified file 'cmake/src/mir/CMakeLists.txt'
355--- cmake/src/mir/CMakeLists.txt 2013-03-13 04:54:15 +0000
356+++ cmake/src/mir/CMakeLists.txt 2014-04-07 13:29:13 +0000
357@@ -17,3 +17,8 @@
358 mir_test_memory_error PROPERTIES
359 RUNTIME_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/mir_gtest
360 )
361+
362+file(INSTALL ${CMAKE_CURRENT_SOURCE_DIR}/fail_on_success.sh
363+ DESTINATION ${CMAKE_BINARY_DIR}/mir_gtest
364+ USE_SOURCE_PERMISSIONS
365+)
366
367=== added file 'cmake/src/mir/fail_on_success.sh'
368--- cmake/src/mir/fail_on_success.sh 1970-01-01 00:00:00 +0000
369+++ cmake/src/mir/fail_on_success.sh 2014-04-07 13:29:13 +0000
370@@ -0,0 +1,8 @@
371+#!/bin/sh
372+
373+$@
374+
375+if [ $? -eq 0 ] ; then
376+ exit 1;
377+fi
378+exit 0;
379
380=== modified file 'cmake/src/mir/mir_discover_gtest_tests.cpp'
381--- cmake/src/mir/mir_discover_gtest_tests.cpp 2014-03-06 06:05:17 +0000
382+++ cmake/src/mir/mir_discover_gtest_tests.cpp 2014-04-07 13:29:13 +0000
383@@ -234,6 +234,18 @@
384 }
385 }
386
387+bool is_death_test(string const& test)
388+{
389+ // precondition: test will match Foo.*
390+ // assumption: death tests will match FooDeathTest.*
391+ bool death_test = false;
392+ if (test.size() > strlen("DeathTest.*"))
393+ death_test = test.substr(test.size() - strlen("DeathTest.*"),
394+ strlen("DeathTest")) == "DeathTest";
395+
396+ return death_test;
397+}
398+
399 int main (int argc, char **argv)
400 {
401 int output_width = get_output_width();
402@@ -291,8 +303,9 @@
403 snprintf(
404 cmd_line,
405 sizeof(cmd_line),
406- config.enable_memcheck ? memcheck_cmd_line_pattern(config.suppressions).c_str() :
407- ordinary_cmd_line_pattern().c_str(),
408+ (config.enable_memcheck && !is_death_test(*test)) ?
409+ memcheck_cmd_line_pattern(config.suppressions).c_str() :
410+ ordinary_cmd_line_pattern().c_str(),
411 test_suite.c_str(),
412 elide_string_left(*test, output_width/2).c_str(),
413 config.executable,
414
415=== modified file 'debian/changelog'
416--- debian/changelog 2014-03-18 18:38:01 +0000
417+++ debian/changelog 2014-04-07 13:29:13 +0000
418@@ -1,3 +1,69 @@
419+mir (0.1.8-0ubuntu1) UNRELEASED; urgency=medium
420+
421+ * New upstream release 0.1.8 (https://launchpad.net/mir/+milestone/0.1.8)
422+ - mirclient ABI unchanged, still at 7. Clients do not need rebuilding.
423+ - mirserver ABI bumped to 18. Shells need rebuilding.
424+ - Server API changes affecting shells:
425+ . GLRenderer::tessellate() changed syntax.
426+ . graphics::Platform::create_display() has a new parameter allowing you
427+ to customize the compositor's (E)GL configutation.
428+ . Renderable::buffer(unsigned long frameno) is now:
429+ Renderable::buffer(void const* user_id). See below.
430+ . Renderable::should_be_rendered_in() is replaced by a more natural:
431+ Renderable::visble()
432+ . input::Surface::name() returns by value instead of reference now,
433+ to ensure future thread safety.
434+ - Switched EventHub device enumeration and hotplug to Udev. NOTE! This
435+ means mir_test_* can't run natively on touch devices any more without
436+ some setup first:
437+ sudo mount -o remount,rw /
438+ sudo apt-get update
439+ sudo apt-get install -y umockdev
440+ umockdev-run -- bin/mir_unit_tests
441+ - Added logging for HWC events.
442+ - Continued consolidation of Surface classes toward a simpler architecture.
443+ - Introduced "RenderableList" as the way to sample the Scene contents,
444+ and started using that in the default compositor.
445+ - Introduced physical length units and conversion (geometry::Length) in
446+ preparation for arbitrary DPI rendering.
447+ - Added some decorations to demo-shell; shadows and basic title bars, all
448+ anti-aliased and high-DPI scalable.
449+ - Multi-monitor frame sync has been redesigned to eliminate the need for
450+ frame number tracking.
451+ - Bugs (and enhancements) resolved:
452+ . [enhancement] Please move input detection to libudev (LP: #1237784)
453+ . [enhancement] Add a clamping resize mode to GLRenderer (LP: #1259887)
454+ . [regression] Intermittent loss of multimonitor frame sync
455+ (LP: #1290306)
456+ . [enhancement] Make GL config options configurable (LP: #1290780)
457+ . memcheck-test doesn't test anything when DISABLED_GTEST_DISCOVERY is
458+ enabled (LP: #1291876)
459+ . "Error opening DRM device" is always followed by "Unknown error -(some
460+ negative number)" (LP: #1292384)
461+ . Rendering/composition gets stopped early (LP: #1293896)
462+ . Ubuntu Touch Settings and terminal apps are not rendering correctly on
463+ rotate. (LP: #1294048)
464+ . [regression] Apps are much slower to open (LP: #1294051)
465+ . Settings app opens to a blank screen unless given enough time to render
466+ or the app is touched (LP: #1294053)
467+ . TestClientInput/DemoPrivateProtobuf memory leak is causing regular CI
468+ test failures (LP: #1295231)
469+ . OSK touch events "fall through" and hit surface behind them
470+ (LP: #1297878)
471+ . [enhancement] add a test for composite of last client post
472+ (LP: #1298596)
473+ . [regression] Surfaces vanish as soon as their edges touch the edge of
474+ screen (LP: #1301115)
475+ * Cherry-picked from future release 0.1.9:
476+ - Bug fix: mirplatformgraphics does not have boost program options in its
477+ symbol table (LP: #1301040)
478+ - Bug fix: unity8 crashed with SIGSEGV in glDeleteTextures() from
479+ mir::scene::GLPixelBuffer::~GLPixelBuffer() from
480+ mir::scene::ThreadedSnapshotStrategy::~ThreadedSnapshotStrategy()
481+ (LP: #1256360)
482+
483+ -- Daniel van Vugt <daniel.van.vugt@canonical.com> Thu, 20 Mar 2014 14:05:25 +0800
484+
485 mir (0.1.7+14.04.20140318-0ubuntu1) trusty; urgency=low
486
487 [ Alberto Aguirre ]
488
489=== modified file 'debian/control'
490--- debian/control 2014-03-17 07:35:22 +0000
491+++ debian/control 2014-04-07 13:29:13 +0000
492@@ -31,7 +31,7 @@
493 libgoogle-glog-dev,
494 liblttng-ust-dev,
495 libxkbcommon-dev,
496- libumockdev-dev,
497+ libumockdev-dev (>= 0.6),
498 umockdev,
499 libudev-dev,
500 google-mock (>= 1.6.0+svn437),
501@@ -70,7 +70,7 @@
502 .
503 Contains the protocol's definition files.
504
505-Package: libmirserver17
506+Package: libmirserver18
507 Section: libs
508 Architecture: i386 amd64 armhf arm64
509 Multi-Arch: same
510@@ -148,7 +148,7 @@
511 Architecture: i386 amd64 armhf arm64
512 Multi-Arch: same
513 Pre-Depends: ${misc:Pre-Depends}
514-Depends: libmirserver17 (= ${binary:Version}),
515+Depends: libmirserver18 (= ${binary:Version}),
516 libmirprotobuf-dev (= ${binary:Version}),
517 mircommon-dev (= ${binary:Version}),
518 libglm-dev,
519
520=== renamed file 'debian/libmirserver17.install' => 'debian/libmirserver18.install'
521--- debian/libmirserver17.install 2014-03-12 06:41:13 +0000
522+++ debian/libmirserver18.install 2014-04-07 13:29:13 +0000
523@@ -1,1 +1,1 @@
524-usr/lib/*/libmirserver.so.17
525+usr/lib/*/libmirserver.so.18
526
527=== added file 'deploy-and-test.sh'
528--- deploy-and-test.sh 1970-01-01 00:00:00 +0000
529+++ deploy-and-test.sh 2014-04-07 13:29:13 +0000
530@@ -0,0 +1,21 @@
531+#!/bin/sh
532+
533+if [ ! -d build-android-arm ] ; then
534+ echo "Built tree not found in $(pwd)/build-android-arm"
535+ exit 1
536+fi
537+
538+# Unpack umockdev requirements
539+( cd build-android-arm ;
540+ apt-get download umockdev:armhf libumockdev0:armhf ;
541+ dpkg -x umockdev_*armhf*.deb . ;
542+ dpkg -x libumockdev0_*armhf*.deb .
543+)
544+
545+adb push build-android-arm/bin /home/phablet/mir/bin
546+adb push build-android-arm/lib /home/phablet/mir/lib
547+adb push build-android-arm/usr /home/phablet/mir/usr
548+
549+adb shell "LD_LIBRARY_PATH=/home/phablet/mir/usr/lib/arm-linux-gnueabihf/:/home/phablet/mir/lib PATH=$PATH:/home/phablet/mir/usr/bin bash -c \"cd /home/phablet/mir/usr/bin ; umockdev-run /home/phablet/mir/bin/mir_unit_tests\""
550+adb shell "LD_LIBRARY_PATH=/home/phablet/mir/usr/lib/arm-linux-gnueabihf/:/home/phablet/mir/lib PATH=$PATH:/home/phablet/mir/usr/bin bash -c \"cd /home/phablet/mir/usr/bin ; umockdev-run /home/phablet/mir/bin/mir_integration_tests\""
551+adb shell "LD_LIBRARY_PATH=/home/phablet/mir/usr/lib/arm-linux-gnueabihf/:/home/phablet/mir/lib PATH=$PATH:/home/phablet/mir/usr/bin bash -c \"cd /home/phablet/mir/usr/bin ; umockdev-run /home/phablet/mir/bin/mir_acceptance_tests\""
552
553=== modified file 'examples/demo-shell/demo_renderer.cpp'
554--- examples/demo-shell/demo_renderer.cpp 2014-03-05 04:13:32 +0000
555+++ examples/demo-shell/demo_renderer.cpp 2014-04-07 13:29:13 +0000
556@@ -17,13 +17,131 @@
557 */
558
559 #include "demo_renderer.h"
560+#include <mir/graphics/renderable.h>
561+#include <cmath>
562
563 using namespace mir;
564 using namespace mir::examples;
565
566+namespace
567+{
568+
569+float penumbra_curve(float x)
570+{
571+ return 1.0f - std::sin(x * M_PI / 2.0f);
572+}
573+
574+GLuint generate_shadow_corner_texture(float opacity)
575+{
576+ struct Texel
577+ {
578+ GLubyte luminance;
579+ GLubyte alpha;
580+ };
581+
582+ int const width = 256;
583+ Texel image[width][width];
584+
585+ int const max = width - 1;
586+ for (int y = 0; y < width; ++y)
587+ {
588+ float curve_y = opacity * 255.0f *
589+ penumbra_curve(static_cast<float>(y) / max);
590+ for (int x = 0; x < width; ++x)
591+ {
592+ Texel *t = &image[y][x];
593+ t->luminance = 0;
594+ t->alpha = curve_y * penumbra_curve(static_cast<float>(x) / max);
595+ }
596+ }
597+
598+ GLuint corner;
599+ glGenTextures(1, &corner);
600+ glBindTexture(GL_TEXTURE_2D, corner);
601+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
602+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
603+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
604+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
605+ glTexImage2D(GL_TEXTURE_2D, 0, GL_LUMINANCE_ALPHA,
606+ width, width, 0, GL_LUMINANCE_ALPHA, GL_UNSIGNED_BYTE,
607+ image);
608+
609+ return corner;
610+}
611+
612+GLuint generate_frame_corner_texture()
613+{
614+ struct Texel
615+ {
616+ GLubyte r, g, b, a;
617+ };
618+
619+ int const width = 256;
620+ Texel image[width][width];
621+
622+ int cx = width / 2;
623+ int cy = width / 2;
624+ int radius_sqr = cx * cx;
625+
626+ for (int y = 0; y < width; ++y)
627+ {
628+ for (int x = 0; x < width; ++x)
629+ {
630+ GLubyte lum = 128;
631+ GLubyte alpha = 255;
632+
633+ // Cut out the corner in a circular shape.
634+ if (x < cx && y < cy)
635+ {
636+ int dx = cx - x;
637+ int dy = cy - y;
638+ if (dx * dx + dy * dy >= radius_sqr)
639+ alpha = 0;
640+ }
641+
642+ // Set gradient
643+ if (y < cy)
644+ {
645+ float brighten = (1.0f - (static_cast<float>(y) / cy));
646+ if (x < cx)
647+ brighten *= std::sin(x * M_PI / width);
648+
649+ lum += (255 - lum) * brighten;
650+ }
651+
652+ image[y][x] = {lum, lum, lum, alpha};
653+ }
654+ }
655+
656+ GLuint corner;
657+ glGenTextures(1, &corner);
658+ glBindTexture(GL_TEXTURE_2D, corner);
659+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER,
660+ GL_LINEAR_MIPMAP_LINEAR);
661+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
662+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
663+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
664+ glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA,
665+ width, width, 0, GL_RGBA, GL_UNSIGNED_BYTE,
666+ image);
667+ glGenerateMipmap(GL_TEXTURE_2D); // Antialiasing please
668+
669+ return corner;
670+}
671+
672+} // namespace
673+
674 DemoRenderer::DemoRenderer(geometry::Rectangle const& display_area)
675 : GLRenderer(display_area)
676 {
677+ shadow_corner_tex = generate_shadow_corner_texture(0.4f);
678+ titlebar_corner_tex = generate_frame_corner_texture();
679+}
680+
681+DemoRenderer::~DemoRenderer()
682+{
683+ glDeleteTextures(1, &shadow_corner_tex);
684+ glDeleteTextures(1, &titlebar_corner_tex);
685 }
686
687 void DemoRenderer::begin() const
688@@ -31,3 +149,156 @@
689 glClearColor(0.2f, 0.2f, 0.2f, 1.0f);
690 glClear(GL_COLOR_BUFFER_BIT);
691 }
692+
693+void DemoRenderer::tessellate(std::vector<Primitive>& primitives,
694+ graphics::Renderable const& renderable,
695+ geometry::Size const& buf_size) const
696+{
697+ GLRenderer::tessellate(primitives, renderable, buf_size);
698+ tessellate_shadow(primitives, renderable, 80.0f);
699+ tessellate_frame(primitives, renderable, 30.0f);
700+}
701+
702+void DemoRenderer::tessellate_shadow(std::vector<Primitive>& primitives,
703+ graphics::Renderable const& renderable,
704+ float radius) const
705+{
706+ auto const& rect = renderable.screen_position();
707+ GLfloat left = rect.top_left.x.as_int();
708+ GLfloat right = left + rect.size.width.as_int();
709+ GLfloat top = rect.top_left.y.as_int();
710+ GLfloat bottom = top + rect.size.height.as_int();
711+
712+ auto n = primitives.size();
713+ primitives.resize(n + 8);
714+
715+ GLfloat rightr = right + radius;
716+ GLfloat leftr = left - radius;
717+ GLfloat topr = top - radius;
718+ GLfloat bottomr = bottom + radius;
719+
720+ auto& right_shadow = primitives[n++];
721+ right_shadow.tex_id = shadow_corner_tex;
722+ right_shadow.type = GL_TRIANGLE_FAN;
723+ right_shadow.vertices.resize(4);
724+ right_shadow.vertices[0] = {{right, top, 0.0f}, {0.0f, 0.0f}};
725+ right_shadow.vertices[1] = {{rightr, top, 0.0f}, {1.0f, 0.0f}};
726+ right_shadow.vertices[2] = {{rightr, bottom, 0.0f}, {1.0f, 0.0f}};
727+ right_shadow.vertices[3] = {{right, bottom, 0.0f}, {0.0f, 0.0f}};
728+
729+ auto& left_shadow = primitives[n++];
730+ left_shadow.tex_id = shadow_corner_tex;
731+ left_shadow.type = GL_TRIANGLE_FAN;
732+ left_shadow.vertices.resize(4);
733+ left_shadow.vertices[0] = {{leftr, top, 0.0f}, {1.0f, 0.0f}};
734+ left_shadow.vertices[1] = {{left, top, 0.0f}, {0.0f, 0.0f}};
735+ left_shadow.vertices[2] = {{left, bottom, 0.0f}, {0.0f, 0.0f}};
736+ left_shadow.vertices[3] = {{leftr, bottom, 0.0f}, {1.0f, 0.0f}};
737+
738+ auto& top_shadow = primitives[n++];
739+ top_shadow.tex_id = shadow_corner_tex;
740+ top_shadow.type = GL_TRIANGLE_FAN;
741+ top_shadow.vertices.resize(4);
742+ top_shadow.vertices[0] = {{left, topr, 0.0f}, {1.0f, 0.0f}};
743+ top_shadow.vertices[1] = {{right, topr, 0.0f}, {1.0f, 0.0f}};
744+ top_shadow.vertices[2] = {{right, top, 0.0f}, {0.0f, 0.0f}};
745+ top_shadow.vertices[3] = {{left, top, 0.0f}, {0.0f, 0.0f}};
746+
747+ auto& bottom_shadow = primitives[n++];
748+ bottom_shadow.tex_id = shadow_corner_tex;
749+ bottom_shadow.type = GL_TRIANGLE_FAN;
750+ bottom_shadow.vertices.resize(4);
751+ bottom_shadow.vertices[0] = {{left, bottom, 0.0f}, {0.0f, 0.0f}};
752+ bottom_shadow.vertices[1] = {{right, bottom, 0.0f}, {0.0f, 0.0f}};
753+ bottom_shadow.vertices[2] = {{right, bottomr, 0.0f}, {1.0f, 0.0f}};
754+ bottom_shadow.vertices[3] = {{left, bottomr, 0.0f}, {1.0f, 0.0f}};
755+
756+ auto& tr_shadow = primitives[n++];
757+ tr_shadow.tex_id = shadow_corner_tex;
758+ tr_shadow.type = GL_TRIANGLE_FAN;
759+ tr_shadow.vertices.resize(4);
760+ tr_shadow.vertices[0] = {{right, top, 0.0f}, {0.0f, 0.0f}};
761+ tr_shadow.vertices[1] = {{right, topr, 0.0f}, {1.0f, 0.0f}};
762+ tr_shadow.vertices[2] = {{rightr, topr, 0.0f}, {1.0f, 1.0f}};
763+ tr_shadow.vertices[3] = {{rightr, top, 0.0f}, {0.0f, 1.0f}};
764+
765+ auto& br_shadow = primitives[n++];
766+ br_shadow.tex_id = shadow_corner_tex;
767+ br_shadow.type = GL_TRIANGLE_FAN;
768+ br_shadow.vertices.resize(4);
769+ br_shadow.vertices[0] = {{right, bottom, 0.0f}, {0.0f, 0.0f}};
770+ br_shadow.vertices[1] = {{rightr, bottom, 0.0f}, {1.0f, 0.0f}};
771+ br_shadow.vertices[2] = {{rightr, bottomr, 0.0f}, {1.0f, 1.0f}};
772+ br_shadow.vertices[3] = {{right, bottomr, 0.0f}, {0.0f, 1.0f}};
773+
774+ auto& bl_shadow = primitives[n++];
775+ bl_shadow.tex_id = shadow_corner_tex;
776+ bl_shadow.type = GL_TRIANGLE_FAN;
777+ bl_shadow.vertices.resize(4);
778+ bl_shadow.vertices[0] = {{left, bottom, 0.0f}, {0.0f, 0.0f}};
779+ bl_shadow.vertices[1] = {{left, bottomr, 0.0f}, {1.0f, 0.0f}};
780+ bl_shadow.vertices[2] = {{leftr, bottomr, 0.0f}, {1.0f, 1.0f}};
781+ bl_shadow.vertices[3] = {{leftr, bottom, 0.0f}, {0.0f, 1.0f}};
782+
783+ auto& tl_shadow = primitives[n++];
784+ tl_shadow.tex_id = shadow_corner_tex;
785+ tl_shadow.type = GL_TRIANGLE_FAN;
786+ tl_shadow.vertices.resize(4);
787+ tl_shadow.vertices[0] = {{left, top, 0.0f}, {0.0f, 0.0f}};
788+ tl_shadow.vertices[1] = {{leftr, top, 0.0f}, {1.0f, 0.0f}};
789+ tl_shadow.vertices[2] = {{leftr, topr, 0.0f}, {1.0f, 1.0f}};
790+ tl_shadow.vertices[3] = {{left, topr, 0.0f}, {0.0f, 1.0f}};
791+
792+ // Shadows always need blending...
793+ glEnable(GL_BLEND);
794+ glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
795+}
796+
797+void DemoRenderer::tessellate_frame(std::vector<Primitive>& primitives,
798+ graphics::Renderable const& renderable,
799+ float titlebar_height) const
800+{
801+ auto const& rect = renderable.screen_position();
802+ GLfloat left = rect.top_left.x.as_int();
803+ GLfloat right = left + rect.size.width.as_int();
804+ GLfloat top = rect.top_left.y.as_int();
805+
806+ auto n = primitives.size();
807+ primitives.resize(n + 3);
808+
809+ GLfloat htop = top - titlebar_height;
810+ GLfloat inleft = left + titlebar_height; // Square proportions for corners
811+ GLfloat inright = right - titlebar_height;
812+
813+ GLfloat mid = (left + right) / 2.0f;
814+ if (inleft > mid) inleft = mid;
815+ if (inright < mid) inright = mid;
816+
817+ auto& top_left_corner = primitives[n++];
818+ top_left_corner.tex_id = titlebar_corner_tex;
819+ top_left_corner.type = GL_TRIANGLE_FAN;
820+ top_left_corner.vertices.resize(4);
821+ top_left_corner.vertices[0] = {{left, htop, 0.0f}, {0.0f, 0.0f}};
822+ top_left_corner.vertices[1] = {{inleft, htop, 0.0f}, {1.0f, 0.0f}};
823+ top_left_corner.vertices[2] = {{inleft, top, 0.0f}, {1.0f, 1.0f}};
824+ top_left_corner.vertices[3] = {{left, top, 0.0f}, {0.0f, 1.0f}};
825+
826+ auto& top_right_corner = primitives[n++];
827+ top_right_corner.tex_id = titlebar_corner_tex;
828+ top_right_corner.type = GL_TRIANGLE_FAN;
829+ top_right_corner.vertices.resize(4);
830+ top_right_corner.vertices[0] = {{inright, htop, 0.0f}, {1.0f, 0.0f}};
831+ top_right_corner.vertices[1] = {{right, htop, 0.0f}, {0.0f, 0.0f}};
832+ top_right_corner.vertices[2] = {{right, top, 0.0f}, {0.0f, 1.0f}};
833+ top_right_corner.vertices[3] = {{inright, top, 0.0f}, {1.0f, 1.0f}};
834+
835+ auto& titlebar = primitives[n++];
836+ titlebar.tex_id = titlebar_corner_tex;
837+ titlebar.type = GL_TRIANGLE_FAN;
838+ titlebar.vertices.resize(4);
839+ titlebar.vertices[0] = {{inleft, htop, 0.0f}, {1.0f, 0.0f}};
840+ titlebar.vertices[1] = {{inright, htop, 0.0f}, {1.0f, 0.0f}};
841+ titlebar.vertices[2] = {{inright, top, 0.0f}, {1.0f, 1.0f}};
842+ titlebar.vertices[3] = {{inleft, top, 0.0f}, {1.0f, 1.0f}};
843+}
844+
845
846=== modified file 'examples/demo-shell/demo_renderer.h'
847--- examples/demo-shell/demo_renderer.h 2014-02-14 09:58:06 +0000
848+++ examples/demo-shell/demo_renderer.h 2014-04-07 13:29:13 +0000
849@@ -30,7 +30,22 @@
850 {
851 public:
852 DemoRenderer(geometry::Rectangle const& display_area);
853+ ~DemoRenderer();
854+
855 void begin() const override;
856+ void tessellate(std::vector<Primitive>& primitives,
857+ graphics::Renderable const& renderable,
858+ geometry::Size const& buf_size) const override;
859+ void tessellate_shadow(std::vector<Primitive>& primitives,
860+ graphics::Renderable const& renderable,
861+ float radius) const;
862+ void tessellate_frame(std::vector<Primitive>& primitives,
863+ graphics::Renderable const& renderable,
864+ float titlebar_height) const;
865+
866+private:
867+ GLuint shadow_corner_tex;
868+ GLuint titlebar_corner_tex;
869 };
870
871 } // namespace examples
872
873=== modified file 'examples/render_overlays.cpp'
874--- examples/render_overlays.cpp 2014-03-17 07:35:22 +0000
875+++ examples/render_overlays.cpp 2014-04-07 13:29:13 +0000
876@@ -105,17 +105,17 @@
877 {
878 }
879
880- std::shared_ptr<mg::Buffer> buffer(unsigned long) const override
881+ std::shared_ptr<mg::Buffer> buffer(void const*) const override
882 {
883 return client->last_rendered();
884 }
885
886- bool alpha_enabled() const
887+ bool alpha_enabled() const override
888 {
889 return false;
890 }
891
892- geom::Rectangle screen_position() const
893+ geom::Rectangle screen_position() const override
894 {
895 return position;
896 }
897@@ -130,14 +130,14 @@
898 return trans;
899 }
900
901- bool shaped() const
902+ bool shaped() const override
903 {
904 return false;
905 }
906
907- bool should_be_rendered_in(geom::Rectangle const& rect) const override
908+ bool visible() const override
909 {
910- return rect.overlaps(position);
911+ return true;
912 }
913
914 int buffers_ready_for_compositor() const override
915@@ -168,7 +168,9 @@
916 mir::DefaultServerConfiguration conf{argc, argv};
917
918 auto platform = conf.the_graphics_platform();
919- auto display = platform->create_display(conf.the_display_configuration_policy());
920+ auto display = platform->create_display(
921+ conf.the_display_configuration_policy(),
922+ conf.the_gl_config());
923 auto buffer_allocator = platform->create_buffer_allocator(conf.the_buffer_initializer());
924
925 mg::BufferProperties buffer_properties{
926
927=== modified file 'examples/render_surfaces.cpp'
928--- examples/render_surfaces.cpp 2014-03-11 04:03:54 +0000
929+++ examples/render_surfaces.cpp 2014-04-07 13:29:13 +0000
930@@ -31,7 +31,8 @@
931 #include "mir/graphics/display_buffer.h"
932 #include "mir/graphics/gl_context.h"
933 #include "mir/shell/surface_factory.h"
934-#include "mir/shell/surface.h"
935+#include "mir/scene/surface.h"
936+#include "mir/scene/surface_coordinator.h"
937 #include "mir/run_mir.h"
938 #include "mir/report_exception.h"
939 #include "mir/raii.h"
940@@ -41,6 +42,9 @@
941 #include "image_renderer.h"
942 #include "server_configuration.h"
943
944+#define GLM_FORCE_RADIANS
945+#include <glm/gtc/matrix_transform.hpp>
946+
947 #include <thread>
948 #include <atomic>
949 #include <chrono>
950@@ -90,6 +94,7 @@
951 std::weak_ptr<mg::Cursor> cursor;
952 static const uint32_t bg_color = 0x00000000;
953 static const uint32_t fg_color = 0xffdd4814;
954+static const float min_alpha = 0.3f;
955
956 void update_cursor(uint32_t bg_color, uint32_t fg_color)
957 {
958@@ -233,8 +238,16 @@
959 y = new_y;
960 }
961
962- surface->set_rotation(total_elapsed_sec * 120.0f, rotation_axis);
963- surface->set_alpha(0.5 + 0.5 * sin(alpha_offset + 2 * M_PI * total_elapsed_sec / 3.0));
964+ glm::mat4 trans = glm::rotate(glm::mat4(1.0f),
965+ glm::radians(total_elapsed_sec * 120.0f),
966+ rotation_axis);
967+ surface->set_transformation(trans);
968+
969+ float const alpha_amplitude = (1.0f - min_alpha) / 2.0f;
970+ surface->set_alpha(min_alpha + alpha_amplitude +
971+ alpha_amplitude *
972+ sin(alpha_offset + 2 * M_PI * total_elapsed_sec /
973+ 3.0));
974 }
975
976 private:
977@@ -433,7 +446,7 @@
978 std::cout << "Rendering " << moveables.size() << " surfaces" << std::endl;
979
980 auto const display = the_display();
981- auto const surface_factory = the_scene_surface_factory();
982+ auto const surface_coordinator = the_surface_coordinator();
983 /* TODO: Get proper configuration */
984 geom::Rectangles view_area;
985 display->for_each_display_buffer([&view_area](mg::DisplayBuffer const& db)
986@@ -452,12 +465,11 @@
987 int i = 0;
988 for (auto& m : moveables)
989 {
990- auto const s = surface_factory->create_surface(
991- nullptr,
992+ auto const s = surface_coordinator->add_surface(
993 msh::a_surface().of_size(surface_size)
994 .of_pixel_format(surface_pf)
995 .of_buffer_usage(mg::BufferUsage::hardware),
996- mf::SurfaceId(), {});
997+ {});
998
999 /*
1000 * We call swap_buffers() twice so that the surface is
1001
1002=== modified file 'include/platform/mir/graphics/display_buffer.h'
1003--- include/platform/mir/graphics/display_buffer.h 2014-03-06 06:05:17 +0000
1004+++ include/platform/mir/graphics/display_buffer.h 2014-04-07 13:29:13 +0000
1005@@ -20,11 +20,11 @@
1006 #define MIR_GRAPHICS_DISPLAY_BUFFER_H_
1007
1008 #include <mir/geometry/rectangle.h>
1009+#include <mir/graphics/renderable.h>
1010 #include <mir_toolkit/common.h>
1011
1012 #include <memory>
1013 #include <functional>
1014-#include <list>
1015
1016 namespace mir
1017 {
1018@@ -32,7 +32,6 @@
1019 {
1020
1021 class Buffer;
1022-class Renderable;
1023
1024 /**
1025 * Interface to an output framebuffer.
1026@@ -57,7 +56,7 @@
1027 that Renderable via OpenGL, or via another method. If the Renderable is to be rendered
1028 via OpenGL, render_fn will be invoked on that Renderable. */
1029 virtual void render_and_post_update(
1030- std::list<std::shared_ptr<Renderable>> const& renderlist,
1031+ RenderableList const& renderlist,
1032 std::function<void(Renderable const&)> const& render_fn) = 0;
1033
1034 /** to be deprecated */
1035
1036=== added file 'include/platform/mir/graphics/gl_config.h'
1037--- include/platform/mir/graphics/gl_config.h 1970-01-01 00:00:00 +0000
1038+++ include/platform/mir/graphics/gl_config.h 2014-04-07 13:29:13 +0000
1039@@ -0,0 +1,54 @@
1040+/*
1041+ * Copyright © 2014 Canonical Ltd.
1042+ *
1043+ * This program is free software: you can redistribute it and/or modify it
1044+ * under the terms of the GNU Lesser General Public License version 3,
1045+ * as published by the Free Software Foundation.
1046+ *
1047+ * This program is distributed in the hope that it will be useful,
1048+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
1049+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
1050+ * GNU Lesser General Public License for more details.
1051+ *
1052+ * You should have received a copy of the GNU Lesser General Public License
1053+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
1054+ *
1055+ * Authored by: Alexandros Frantzis <alexandros.frantzis@canonical.com>
1056+ */
1057+
1058+#ifndef MIR_GRAPHICS_GL_CONFIG_H_
1059+#define MIR_GRAPHICS_GL_CONFIG_H_
1060+
1061+namespace mir
1062+{
1063+namespace graphics
1064+{
1065+
1066+/**
1067+ * Interface for customizing aspects of the GL config used by the server.
1068+ */
1069+class GLConfig
1070+{
1071+public:
1072+ virtual ~GLConfig() = default;
1073+
1074+ /**
1075+ * Gets the bits to use for each pixel in the depth buffer.
1076+ */
1077+ virtual int depth_buffer_bits() const = 0;
1078+
1079+ /**
1080+ * Gets the bits to use for each pixel in the stencil buffer.
1081+ */
1082+ virtual int stencil_buffer_bits() const = 0;
1083+
1084+protected:
1085+ GLConfig() = default;
1086+ GLConfig(GLConfig const&) = delete;
1087+ GLConfig& operator=(GLConfig const&) = delete;
1088+};
1089+
1090+}
1091+}
1092+
1093+#endif /* MIR_GRAPHICS_GL_CONFIG_H_ */
1094
1095=== modified file 'include/platform/mir/graphics/platform.h'
1096--- include/platform/mir/graphics/platform.h 2014-03-06 06:05:17 +0000
1097+++ include/platform/mir/graphics/platform.h 2014-04-07 13:29:13 +0000
1098@@ -22,6 +22,7 @@
1099
1100 #include "basic_platform.h"
1101
1102+#include <boost/program_options/options_description.hpp>
1103 #include <memory>
1104
1105 namespace mir
1106@@ -48,6 +49,7 @@
1107 class DisplayReport;
1108 class DisplayConfigurationPolicy;
1109 class GraphicBufferAllocator;
1110+class GLConfig;
1111
1112 /**
1113 * \defgroup platform_enablement Mir platform enablement
1114@@ -81,7 +83,8 @@
1115 * Creates the display subsystem.
1116 */
1117 virtual std::shared_ptr<Display> create_display(
1118- std::shared_ptr<DisplayConfigurationPolicy> const& initial_conf_policy) = 0;
1119+ std::shared_ptr<DisplayConfigurationPolicy> const& initial_conf_policy,
1120+ std::shared_ptr<GLConfig> const& gl_config) = 0;
1121
1122 /**
1123 * Gets the IPC package for the platform.
1124@@ -119,6 +122,10 @@
1125 */
1126 extern "C" typedef std::shared_ptr<Platform>(*CreatePlatform)(std::shared_ptr<options::Option> const& options, std::shared_ptr<DisplayReport> const& report);
1127 extern "C" std::shared_ptr<Platform> create_platform (std::shared_ptr<options::Option> const& options, std::shared_ptr<DisplayReport> const& report);
1128+extern "C" typedef void(*AddPlatformOptions)(
1129+ boost::program_options::options_description& config);
1130+extern "C" void add_platform_options(
1131+ boost::program_options::options_description& config);
1132 }
1133 }
1134
1135
1136=== modified file 'include/platform/mir/graphics/renderable.h'
1137--- include/platform/mir/graphics/renderable.h 2014-03-17 07:35:22 +0000
1138+++ include/platform/mir/graphics/renderable.h 2014-04-07 13:29:13 +0000
1139@@ -22,6 +22,7 @@
1140 #include <mir/geometry/rectangle.h>
1141 #include <glm/glm.hpp>
1142 #include <memory>
1143+#include <list>
1144
1145 namespace mir
1146 {
1147@@ -35,19 +36,15 @@
1148 /**
1149 * Return the next buffer that should be composited/rendered.
1150 *
1151- * \param [in] frameno The frameno parameter is important for
1152- * multi-monitor platforms. Calls with the same frameno
1153- * will get the same buffer returned. This ensures that
1154- * a surface visible on multiple outputs does not get
1155- * its buffers consumed any faster than the refresh
1156- * rate of a single monitor. Implementations may ignore
1157- * the value of frameno on single-monitor platforms
1158- * only. The caller should always ensure the frameno
1159- * is different to the previous frame. The exact value
1160- * of frameno is not important but a large range of
1161- * values is recommended.
1162+ * \param [in] user_id An arbitrary unique identifier used to distinguish
1163+ * separate threads/monitors/components which need
1164+ * to concurrently receive the same buffer. Calling
1165+ * with the same user_id will return a new (different)
1166+ * buffer to that user each time. For consistency,
1167+ * all callers need to determine their user_id in the
1168+ * same way (e.g. always use "this" pointer).
1169 */
1170- virtual std::shared_ptr<Buffer> buffer(unsigned long frameno) const = 0;
1171+ virtual std::shared_ptr<Buffer> buffer(void const* user_id) const = 0;
1172
1173 virtual bool alpha_enabled() const = 0;
1174 virtual geometry::Rectangle screen_position() const = 0;
1175@@ -69,7 +66,14 @@
1176 * the surface itself).
1177 */
1178 virtual glm::mat4 transformation() const = 0;
1179- virtual bool should_be_rendered_in(geometry::Rectangle const& rect) const = 0;
1180+
1181+ /**
1182+ * TODO: Its a bit questionable that we have this member function, why not
1183+ * just trim the renderable from the RenderableList? Its convenient
1184+ * to have this function temporarily while refactoring --kdub
1185+ */
1186+ virtual bool visible() const = 0;
1187+
1188 virtual bool shaped() const = 0; // meaning the pixel format has alpha
1189 virtual int buffers_ready_for_compositor() const = 0;
1190
1191@@ -80,6 +84,9 @@
1192 Renderable& operator=(Renderable const&) = delete;
1193 };
1194
1195+// XXX Would performance be better with a vector?
1196+typedef std::list<std::shared_ptr<Renderable>> RenderableList;
1197+
1198 }
1199 }
1200
1201
1202=== modified file 'include/platform/mir/options/default_configuration.h'
1203--- include/platform/mir/options/default_configuration.h 2014-03-17 07:35:22 +0000
1204+++ include/platform/mir/options/default_configuration.h 2014-04-07 13:29:13 +0000
1205@@ -37,6 +37,7 @@
1206 boost::program_options::options_description_easy_init add_options();
1207
1208 private:
1209+ void add_platform_options();
1210 // accessed via the base interface, when access to add_options() has been "lost"
1211 std::shared_ptr<options::Option> the_options() const override;
1212
1213
1214=== added file 'include/platform/mir/shared_library_loader.h'
1215--- include/platform/mir/shared_library_loader.h 1970-01-01 00:00:00 +0000
1216+++ include/platform/mir/shared_library_loader.h 2014-04-07 13:29:13 +0000
1217@@ -0,0 +1,28 @@
1218+/*
1219+ * Copyright © 2013 Canonical Ltd.
1220+ *
1221+ * This program is free software: you can redistribute it and/or modify it
1222+ * under the terms of the GNU Lesser General Public License version 3,
1223+ * as published by the Free Software Foundation.
1224+ *
1225+ * This program is distributed in the hope that it will be useful,
1226+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
1227+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
1228+ * GNU Lesser General Public License for more details.
1229+ *
1230+ * You should have received a copy of the GNU Lesser General Public License
1231+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
1232+ *
1233+ * Authored by: Kevin DuBois <kevin.dubois@canonical.com>
1234+ */
1235+
1236+#ifndef MIR_SHARED_LIBRARY_LOADER_H_
1237+#define MIR_SHARED_LIBRARY_LOADER_H_
1238+
1239+#include <string>
1240+namespace mir
1241+{
1242+class SharedLibrary;
1243+SharedLibrary const* load_library(std::string const& libname);
1244+}
1245+#endif
1246
1247=== modified file 'include/server/mir/compositor/buffer_stream.h'
1248--- include/server/mir/compositor/buffer_stream.h 2014-03-07 03:15:55 +0000
1249+++ include/server/mir/compositor/buffer_stream.h 2014-04-07 13:29:13 +0000
1250@@ -43,7 +43,7 @@
1251
1252 virtual void swap_client_buffers(graphics::Buffer* old_buffer, std::function<void(graphics::Buffer* new_buffer)> complete) = 0;
1253 virtual std::shared_ptr<graphics::Buffer>
1254- lock_compositor_buffer(unsigned long frameno) = 0;
1255+ lock_compositor_buffer(void const* user_id) = 0;
1256 virtual std::shared_ptr<graphics::Buffer> lock_snapshot_buffer() = 0;
1257 virtual MirPixelFormat get_stream_pixel_format() = 0;
1258 virtual geometry::Size stream_size() = 0;
1259
1260=== modified file 'include/server/mir/compositor/gl_renderer.h'
1261--- include/server/mir/compositor/gl_renderer.h 2014-03-17 07:35:22 +0000
1262+++ include/server/mir/compositor/gl_renderer.h 2014-04-07 13:29:13 +0000
1263@@ -54,14 +54,27 @@
1264 GLfloat texcoord[2];
1265 };
1266
1267+ struct Primitive
1268+ {
1269+ GLenum type; // GL_TRIANGLE_STRIP, GL_TRIANGLE_FAN, GL_TRIANGLES etc
1270+ GLuint tex_id; // GL texture ID (or 0 to represent the surface itself)
1271+ std::vector<Vertex> vertices;
1272+ };
1273+
1274 /**
1275 * tessellate defines the list of triangles that will be used to render
1276 * the surface. By default it just returns 4 vertices for a rectangle.
1277 * However you can override its behaviour to tessellate more finely and
1278 * deform freely for effects like wobbly windows.
1279 *
1280- * \returns The mode to be passed to glDrawArrays, e.g. GL_TRIANGLE_STRIP,
1281- * GL_TRIANGLE_FAN or GL_TRIANGLES.
1282+ * \param [in,out] primitives The list of rendering primitives to be
1283+ * grown and/or modified.
1284+ * \param [in] renderable The renderable surface being tessellated.
1285+ * \param [in] buf_size The dimensions of the buffer being rendered,
1286+ * which can be particularly useful in
1287+ * calculating texcoords for a surface being
1288+ * actively resized (as the buf_size doesn't
1289+ * yet match renderable.size()).
1290 *
1291 * \note The cohesion of this function to GLRenderer is quite loose and it
1292 * does not strictly need to reside here.
1293@@ -69,8 +82,18 @@
1294 * the only OpenGL-specific class in the display server, and
1295 * tessellation is very much OpenGL-specific.
1296 */
1297- virtual GLenum tessellate(graphics::Renderable const& renderable,
1298- std::vector<Vertex>& vertices) const;
1299+ virtual void tessellate(std::vector<Primitive>& primitives,
1300+ graphics::Renderable const& renderable,
1301+ geometry::Size const& buf_size) const;
1302+
1303+ /**
1304+ * Load the texture for a surface any which way you like. The default
1305+ * implementation does so with efficient GPU-side caching built in.
1306+ *
1307+ * \returns The OpenGL texture name for the surface.
1308+ */
1309+ virtual GLuint load_texture(graphics::Renderable const& renderable,
1310+ graphics::Buffer& buffer) const;
1311
1312 private:
1313 GLuint vertex_shader;
1314
1315=== modified file 'include/server/mir/compositor/renderer.h'
1316--- include/server/mir/compositor/renderer.h 2014-03-17 07:35:22 +0000
1317+++ include/server/mir/compositor/renderer.h 2014-04-07 13:29:13 +0000
1318@@ -40,8 +40,8 @@
1319 virtual void set_rotation(float degrees) = 0;
1320 virtual void begin() const = 0;
1321
1322- // XXX The buffer parameter here could now be replaced with a "frameno"
1323- // instead, and use renderable.buffer(frameno). Is that better?
1324+ // XXX The buffer parameter here could now be replaced with
1325+ // renderable::buffer().
1326 virtual void render(graphics::Renderable const& renderable,
1327 graphics::Buffer& buffer) const = 0;
1328 virtual void end() const = 0;
1329
1330=== modified file 'include/server/mir/compositor/scene.h'
1331--- include/server/mir/compositor/scene.h 2014-03-17 07:35:22 +0000
1332+++ include/server/mir/compositor/scene.h 2014-04-07 13:29:13 +0000
1333@@ -20,6 +20,7 @@
1334 #define MIR_COMPOSITOR_SCENE_H_
1335
1336 #include "mir/geometry/forward.h"
1337+#include "mir/graphics/renderable.h"
1338
1339 #include <memory>
1340 #include <functional>
1341@@ -62,13 +63,15 @@
1342 public:
1343 virtual ~Scene() {}
1344
1345+ /**
1346+ * Generate a valid list of renderables based on the current state of the Scene.
1347+ * \returns a list of mg::Renderables. The list is in stacking order from back to front.
1348+ */
1349+ virtual graphics::RenderableList generate_renderable_list() const = 0;
1350+
1351 // Back to front; normal rendering order
1352 virtual void for_each_if(FilterForScene& filter, OperatorForScene& op) = 0;
1353
1354- // Front to back; as used when scanning for occlusions
1355- virtual void reverse_for_each_if(FilterForScene& filter,
1356- OperatorForScene& op) = 0;
1357-
1358 /**
1359 * Sets a callback to be called whenever the state of the
1360 * Scene changes.
1361
1362=== modified file 'include/server/mir/default_server_configuration.h'
1363--- include/server/mir/default_server_configuration.h 2014-03-06 06:05:17 +0000
1364+++ include/server/mir/default_server_configuration.h 2014-04-07 13:29:13 +0000
1365@@ -61,7 +61,6 @@
1366 class SessionListener;
1367 class FocusController;
1368 class DisplayLayout;
1369-class SurfaceConfigurator;
1370 }
1371 namespace time
1372 {
1373@@ -69,6 +68,7 @@
1374 }
1375 namespace scene
1376 {
1377+class SurfaceFactory;
1378 class BroadcastingSessionEventSink;
1379 class BufferStreamFactory;
1380 class MediatingDisplayChanger;
1381@@ -78,7 +78,8 @@
1382 class SessionEventHandlerRegister;
1383 class SessionManager;
1384 class SnapshotStrategy;
1385-class SurfaceBuilder;
1386+class SurfaceCoordinator;
1387+class SurfaceConfigurator;
1388 class SurfaceStackModel;
1389 class SurfaceStack;
1390 class SurfaceRanker;
1391@@ -93,6 +94,7 @@
1392 class BufferInitializer;
1393 class DisplayReport;
1394 class GraphicBufferAllocator;
1395+class GLConfig;
1396 namespace nested { class HostConnection; }
1397 }
1398 namespace input
1399@@ -152,6 +154,7 @@
1400 virtual std::shared_ptr<graphics::DisplayConfigurationPolicy> the_display_configuration_policy();
1401 virtual std::shared_ptr<graphics::nested::HostConnection> the_host_connection();
1402 virtual std::shared_ptr<input::EventFilter> the_nested_event_filter();
1403+ virtual std::shared_ptr<graphics::GLConfig> the_gl_config();
1404 /** @} */
1405
1406 /** @name graphics configuration - dependencies
1407@@ -198,12 +201,10 @@
1408 * configurable interfaces for modifying shell
1409 * @{ */
1410 virtual std::shared_ptr<shell::SurfaceFactory> the_shell_surface_factory();
1411- virtual std::shared_ptr<shell::SurfaceFactory> the_scene_surface_factory();
1412 virtual std::shared_ptr<shell::FocusSetter> the_shell_focus_setter();
1413 virtual std::shared_ptr<shell::PlacementStrategy> the_shell_placement_strategy();
1414 virtual std::shared_ptr<shell::SessionListener> the_shell_session_listener();
1415 virtual std::shared_ptr<shell::DisplayLayout> the_shell_display_layout();
1416- virtual std::shared_ptr<shell::SurfaceConfigurator> the_shell_surface_configurator();
1417 /** @} */
1418
1419 /** @name internal scene configuration
1420@@ -216,7 +217,10 @@
1421 virtual std::shared_ptr<scene::SessionEventSink> the_session_event_sink();
1422 virtual std::shared_ptr<scene::SessionEventHandlerRegister> the_session_event_handler_register();
1423 virtual std::shared_ptr<scene::SurfaceStackModel> the_surface_stack_model();
1424- virtual std::shared_ptr<scene::SurfaceRanker> the_surface_ranker();
1425+ virtual std::shared_ptr<scene::SurfaceRanker> the_surface_ranker();
1426+ virtual std::shared_ptr<scene::SurfaceFactory> the_surface_factory();
1427+ virtual std::shared_ptr<scene::SurfaceCoordinator>the_surface_coordinator();
1428+ virtual std::shared_ptr<scene::SurfaceConfigurator> the_surface_configurator();
1429 /** @} */
1430
1431 /** @name scene configuration - dependencies
1432@@ -284,7 +288,7 @@
1433 CachedPtr<scene::SceneReport> scene_report;
1434
1435 CachedPtr<shell::SurfaceFactory> shell_surface_factory;
1436- CachedPtr<shell::SurfaceFactory> scene_surface_factory;
1437+ CachedPtr<scene::SurfaceFactory> surface_factory;
1438 CachedPtr<scene::SessionContainer> session_container;
1439 CachedPtr<shell::FocusSetter> shell_focus_setter;
1440 CachedPtr<shell::PlacementStrategy> shell_placement_strategy;
1441@@ -292,7 +296,7 @@
1442 CachedPtr<scene::PixelBuffer> pixel_buffer;
1443 CachedPtr<scene::SnapshotStrategy> snapshot_strategy;
1444 CachedPtr<shell::DisplayLayout> shell_display_layout;
1445- CachedPtr<shell::SurfaceConfigurator> shell_surface_configurator;
1446+ CachedPtr<scene::SurfaceConfigurator> surface_configurator;
1447 CachedPtr<compositor::DisplayBufferCompositorFactory> display_buffer_compositor_factory;
1448 CachedPtr<compositor::Compositor> compositor;
1449 CachedPtr<compositor::CompositorReport> compositor_report;
1450@@ -304,6 +308,7 @@
1451 CachedPtr<graphics::DisplayConfigurationPolicy> display_configuration_policy;
1452 CachedPtr<graphics::nested::HostConnection> host_connection;
1453 CachedPtr<scene::MediatingDisplayChanger> mediating_display_changer;
1454+ CachedPtr<graphics::GLConfig> gl_config;
1455
1456 private:
1457 std::shared_ptr<options::Configuration> const configuration_options;
1458@@ -321,7 +326,6 @@
1459 std::shared_ptr<scene::BroadcastingSessionEventSink> the_broadcasting_session_event_sink();
1460 std::shared_ptr<input::NestedInputRelay> the_nested_input_relay();
1461 std::shared_ptr<scene::SessionManager> the_session_manager();
1462- std::shared_ptr<scene::SurfaceBuilder> the_surface_builder();
1463 std::shared_ptr<scene::SurfaceController> the_surface_controller();
1464
1465 auto report_factory(char const* report_opt) -> std::unique_ptr<report::ReportFactory>;
1466
1467=== modified file 'include/server/mir/frontend/display_changer.h'
1468--- include/server/mir/frontend/display_changer.h 2013-09-17 20:03:16 +0000
1469+++ include/server/mir/frontend/display_changer.h 2014-04-07 13:29:13 +0000
1470@@ -38,7 +38,6 @@
1471
1472 virtual std::shared_ptr<graphics::DisplayConfiguration> active_configuration() = 0;
1473 virtual void configure(std::shared_ptr<Session> const&, std::shared_ptr<graphics::DisplayConfiguration> const&) = 0;
1474- virtual void ensure_display_powered(std::shared_ptr<Session> const& session) = 0;
1475
1476 protected:
1477 DisplayChanger() = default;
1478
1479=== modified file 'include/server/mir/frontend/session_authorizer.h'
1480--- include/server/mir/frontend/session_authorizer.h 2014-03-06 06:05:17 +0000
1481+++ include/server/mir/frontend/session_authorizer.h 2014-04-07 13:29:13 +0000
1482@@ -29,10 +29,12 @@
1483 class SessionAuthorizer
1484 {
1485 public:
1486- virtual ~SessionAuthorizer() {}
1487+ virtual ~SessionAuthorizer() = default;
1488
1489 virtual bool connection_is_allowed(pid_t pid) = 0;
1490 virtual bool configure_display_is_allowed(pid_t pid) = 0;
1491+ virtual bool screencast_is_allowed(pid_t pid) = 0;
1492+
1493 protected:
1494 SessionAuthorizer() = default;
1495 SessionAuthorizer(SessionAuthorizer const&) = delete;
1496
1497=== modified file 'include/server/mir/input/surface.h'
1498--- include/server/mir/input/surface.h 2014-03-06 06:05:17 +0000
1499+++ include/server/mir/input/surface.h 2014-04-07 13:29:13 +0000
1500@@ -30,7 +30,7 @@
1501 class Surface
1502 {
1503 public:
1504- virtual std::string const& name() const = 0;
1505+ virtual std::string name() const = 0;
1506 virtual geometry::Point top_left() const = 0;
1507 virtual geometry::Size size() const = 0;
1508 virtual bool contains(geometry::Point const& point) const = 0;
1509
1510=== added file 'include/server/mir/scene/surface.h'
1511--- include/server/mir/scene/surface.h 1970-01-01 00:00:00 +0000
1512+++ include/server/mir/scene/surface.h 2014-04-07 13:29:13 +0000
1513@@ -0,0 +1,59 @@
1514+/*
1515+ * Copyright © 2014 Canonical Ltd.
1516+ *
1517+ * This program is free software: you can redistribute it and/or modify it
1518+ * under the terms of the GNU General Public License version 3,
1519+ * as published by the Free Software Foundation.
1520+ *
1521+ * This program is distributed in the hope that it will be useful,
1522+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
1523+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
1524+ * GNU General Public License for more details.
1525+ *
1526+ * You should have received a copy of the GNU General Public License
1527+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
1528+ *
1529+ * Authored by: Alan Griffiths <alan@octopull.co.uk>
1530+ */
1531+
1532+#ifndef MIR_SCENE_SURFACE_H_
1533+#define MIR_SCENE_SURFACE_H_
1534+
1535+#include "mir/graphics/renderable.h"
1536+#include "mir/input/surface.h"
1537+#include "mir/shell/surface.h"
1538+
1539+namespace mir
1540+{
1541+namespace input { class InputChannel; }
1542+
1543+namespace scene
1544+{
1545+class SurfaceObserver;
1546+
1547+class Surface :
1548+ public graphics::Renderable,
1549+ public input::Surface,
1550+ public shell::Surface
1551+{
1552+public:
1553+ // resolve ambiguous member function names
1554+ std::string name() const = 0;
1555+ geometry::Size size() const = 0;
1556+ geometry::Point top_left() const = 0;
1557+ float alpha() const = 0;
1558+
1559+ // member functions that don't exist in base classes
1560+ // TODO input_channel() and on_change() relate to
1561+ // TODO adding and removing the surface from the scene and are probably not
1562+ // TODO cleanest interface for this.
1563+ virtual std::shared_ptr<input::InputChannel> input_channel() const = 0;
1564+ virtual void on_change(std::function<void()> change_notification) = 0;
1565+
1566+ virtual void add_observer(std::shared_ptr<SurfaceObserver> const& observer) = 0;
1567+ virtual void remove_observer(std::shared_ptr<SurfaceObserver> const& observer) = 0;
1568+};
1569+}
1570+}
1571+
1572+#endif // MIR_SCENE_SURFACE_H_
1573
1574=== renamed file 'include/server/mir/shell/surface_configurator.h' => 'include/server/mir/scene/surface_configurator.h'
1575--- include/server/mir/shell/surface_configurator.h 2014-03-06 06:05:17 +0000
1576+++ include/server/mir/scene/surface_configurator.h 2014-04-07 13:29:13 +0000
1577@@ -16,8 +16,8 @@
1578 * Authored by: Robert Carr <robert.carr@canonical.com>
1579 */
1580
1581-#ifndef MIR_SHELL_SURFACE_CONFIGURATOR_H_
1582-#define MIR_SHELL_SURFACE_CONFIGURATOR_H_
1583+#ifndef MIR_SCENE_SURFACE_CONFIGURATOR_H_
1584+#define MIR_SCENE_SURFACE_CONFIGURATOR_H_
1585
1586 #include "mir_toolkit/common.h"
1587
1588@@ -26,7 +26,7 @@
1589 namespace mir
1590 {
1591
1592-namespace shell
1593+namespace scene
1594 {
1595 class Surface;
1596
1597@@ -51,4 +51,4 @@
1598 }
1599 } // namespace mir
1600
1601-#endif // MIR_SHELL_SURFACE_CONFIGURATOR_H_
1602+#endif // MIR_SCENE_SURFACE_CONFIGURATOR_H_
1603
1604=== renamed file 'src/server/scene/surface_builder.h' => 'include/server/mir/scene/surface_coordinator.h'
1605--- src/server/scene/surface_builder.h 2014-03-06 06:05:17 +0000
1606+++ include/server/mir/scene/surface_coordinator.h 2014-04-07 13:29:13 +0000
1607@@ -1,5 +1,5 @@
1608 /*
1609- * Copyright © 2013 Canonical Ltd.
1610+ * Copyright © 2013-14 Canonical Ltd.
1611 *
1612 * This program is free software: you can redistribute it and/or modify it
1613 * under the terms of the GNU General Public License version 3,
1614@@ -17,8 +17,10 @@
1615 */
1616
1617
1618-#ifndef MIR_SCENE_SURFACE_BUILDER_H_
1619-#define MIR_SCENE_SURFACE_BUILDER_H_
1620+#ifndef MIR_SCENE_SURFACE_COORDINATOR_H_
1621+#define MIR_SCENE_SURFACE_COORDINATOR_H_
1622+
1623+#include "mir/scene/surface_ranker.h"
1624
1625 #include <memory>
1626
1627@@ -31,22 +33,25 @@
1628
1629 namespace scene
1630 {
1631-class BasicSurface;
1632+class Surface;
1633+class SurfaceObserver;
1634
1635-class SurfaceBuilder
1636+class SurfaceCoordinator : public SurfaceRanker
1637 {
1638 public:
1639- virtual std::weak_ptr<BasicSurface> create_surface(shell::SurfaceCreationParameters const& params) = 0;
1640+ virtual std::shared_ptr<Surface> add_surface(
1641+ shell::SurfaceCreationParameters const& params,
1642+ std::shared_ptr<SurfaceObserver> const& observer) = 0;
1643
1644- virtual void destroy_surface(std::weak_ptr<BasicSurface> const& surface) = 0;
1645+ virtual void remove_surface(std::weak_ptr<Surface> const& surface) = 0;
1646 protected:
1647- SurfaceBuilder() = default;
1648- virtual ~SurfaceBuilder() = default;
1649- SurfaceBuilder(SurfaceBuilder const&) = delete;
1650- SurfaceBuilder& operator=(SurfaceBuilder const&) = delete;
1651+ SurfaceCoordinator() = default;
1652+ virtual ~SurfaceCoordinator() = default;
1653+ SurfaceCoordinator(SurfaceCoordinator const&) = delete;
1654+ SurfaceCoordinator& operator=(SurfaceCoordinator const&) = delete;
1655 };
1656 }
1657 }
1658
1659
1660-#endif /* MIR_SCENE_SURFACE_BUILDER_H_ */
1661+#endif /* MIR_SCENE_SURFACE_COORDINATOR_H_ */
1662
1663=== added file 'include/server/mir/scene/surface_event_source.h'
1664--- include/server/mir/scene/surface_event_source.h 1970-01-01 00:00:00 +0000
1665+++ include/server/mir/scene/surface_event_source.h 2014-04-07 13:29:13 +0000
1666@@ -0,0 +1,49 @@
1667+/*
1668+ * Copyright © 2014 Canonical Ltd.
1669+ *
1670+ * This program is free software: you can redistribute it and/or modify it
1671+ * under the terms of the GNU General Public License version 3,
1672+ * as published by the Free Software Foundation.
1673+ *
1674+ * This program is distributed in the hope that it will be useful,
1675+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
1676+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
1677+ * GNU General Public License for more details.
1678+ *
1679+ * You should have received a copy of the GNU General Public License
1680+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
1681+ *
1682+ * Authored by: Alan Griffiths <alan@octopull.co.uk>
1683+ */
1684+
1685+#ifndef MIR_SCENE_SURFACE_EVENT_SOURCE_H_
1686+#define MIR_SCENE_SURFACE_EVENT_SOURCE_H_
1687+
1688+#include "mir/scene/surface_observer.h"
1689+#include "mir/frontend/surface_id.h"
1690+#include "mir/frontend/event_sink.h"
1691+
1692+#include <memory>
1693+
1694+namespace mir
1695+{
1696+namespace scene
1697+{
1698+class SurfaceEventSource : public SurfaceObserver
1699+{
1700+public:
1701+ SurfaceEventSource(
1702+ frontend::SurfaceId id,
1703+ std::shared_ptr<frontend::EventSink> const& event_sink);
1704+
1705+ void attrib_change(MirSurfaceAttrib attrib, int value);
1706+ void resize(geometry::Size const& size);
1707+
1708+private:
1709+ frontend::SurfaceId const id;
1710+ std::shared_ptr<frontend::EventSink> const event_sink;
1711+};
1712+}
1713+}
1714+
1715+#endif // MIR_SCENE_SURFACE_EVENT_SOURCE_H_
1716
1717=== renamed file 'src/server/scene/basic_surface_factory.h' => 'include/server/mir/scene/surface_factory.h'
1718--- src/server/scene/basic_surface_factory.h 2014-03-06 06:05:17 +0000
1719+++ include/server/mir/scene/surface_factory.h 2014-04-07 13:29:13 +0000
1720@@ -1,5 +1,5 @@
1721 /*
1722- * Copyright © 2013 Canonical Ltd.
1723+ * Copyright © 2013-2014 Canonical Ltd.
1724 *
1725 * This program is free software: you can redistribute it and/or modify it
1726 * under the terms of the GNU General Public License version 3,
1727@@ -16,33 +16,33 @@
1728 * Authored by: Kevin DuBois <kevin.dubois@canonical.com>
1729 */
1730
1731-#ifndef MIR_SCENE_BASIC_SURFACE_FACTORY_H_
1732-#define MIR_SCENE_BASIC_SURFACE_FACTORY_H_
1733+#ifndef MIR_SCENE_SURFACE_FACTORY_H_
1734+#define MIR_SCENE_SURFACE_FACTORY_H_
1735
1736 #include "mir/shell/surface_creation_parameters.h"
1737 #include <memory>
1738-#include <functional>
1739
1740 namespace mir
1741 {
1742 namespace scene
1743 {
1744+class Surface;
1745
1746-class BasicSurface;
1747-class BasicSurfaceFactory
1748+class SurfaceFactory
1749 {
1750 public:
1751- BasicSurfaceFactory() = default;
1752- virtual ~BasicSurfaceFactory() = default;
1753-
1754- virtual std::shared_ptr<BasicSurface> create_surface(
1755- shell::SurfaceCreationParameters const&, std::function<void()> const&) = 0;
1756+ SurfaceFactory() = default;
1757+ virtual ~SurfaceFactory() = default;
1758+
1759+ virtual std::shared_ptr<Surface> create_surface(
1760+ shell::SurfaceCreationParameters const& params) = 0;
1761+
1762 private:
1763- BasicSurfaceFactory(const BasicSurfaceFactory&) = delete;
1764- BasicSurfaceFactory& operator=(const BasicSurfaceFactory&) = delete;
1765+ SurfaceFactory(const SurfaceFactory&) = delete;
1766+ SurfaceFactory& operator=(const SurfaceFactory&) = delete;
1767 };
1768
1769 }
1770 }
1771
1772-#endif /* MIR_SCENE_BASIC_SURFACE_FACTORY_H_ */
1773+#endif /* MIR_SCENE_SURFACE_FACTORY_H_ */
1774
1775=== added file 'include/server/mir/scene/surface_observer.h'
1776--- include/server/mir/scene/surface_observer.h 1970-01-01 00:00:00 +0000
1777+++ include/server/mir/scene/surface_observer.h 2014-04-07 13:29:13 +0000
1778@@ -0,0 +1,45 @@
1779+/*
1780+ * Copyright © 2014 Canonical Ltd.
1781+ *
1782+ * This program is free software: you can redistribute it and/or modify it
1783+ * under the terms of the GNU General Public License version 3,
1784+ * as published by the Free Software Foundation.
1785+ *
1786+ * This program is distributed in the hope that it will be useful,
1787+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
1788+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
1789+ * GNU General Public License for more details.
1790+ *
1791+ * You should have received a copy of the GNU General Public License
1792+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
1793+ *
1794+ * Authored by: Alan Griffiths <alan@octopull.co.uk>
1795+ */
1796+
1797+#ifndef MIR_SCENE_SURFACE_OBSERVER_H_
1798+#define MIR_SCENE_SURFACE_OBSERVER_H_
1799+
1800+#include "mir/geometry/size.h"
1801+#include "mir_toolkit/common.h"
1802+
1803+namespace mir
1804+{
1805+namespace scene
1806+{
1807+// Initial cut - supporting the frontend requirement, more will follow
1808+class SurfaceObserver
1809+{
1810+public:
1811+ virtual void attrib_change(MirSurfaceAttrib attrib, int value) = 0;
1812+ virtual void resize(geometry::Size const& size) = 0;
1813+
1814+protected:
1815+ SurfaceObserver() = default;
1816+ virtual ~SurfaceObserver() = default;
1817+ SurfaceObserver(SurfaceObserver const&) = delete;
1818+ SurfaceObserver& operator=(SurfaceObserver const&) = delete;
1819+};
1820+}
1821+}
1822+
1823+#endif // MIR_SCENE_SURFACE_OBSERVER_H_
1824
1825=== renamed file 'src/server/scene/surface_ranker.h' => 'include/server/mir/scene/surface_ranker.h'
1826--- src/server/scene/surface_ranker.h 2014-03-06 06:05:17 +0000
1827+++ include/server/mir/scene/surface_ranker.h 2014-04-07 13:29:13 +0000
1828@@ -26,12 +26,12 @@
1829 {
1830 namespace scene
1831 {
1832-class BasicSurface;
1833+class Surface;
1834
1835 class SurfaceRanker
1836 {
1837 public:
1838- virtual void raise(std::weak_ptr<BasicSurface> const& surface) = 0;
1839+ virtual void raise(std::weak_ptr<Surface> const& surface) = 0;
1840
1841 protected:
1842 SurfaceRanker() = default;
1843
1844=== modified file 'include/server/mir/shell/surface.h'
1845--- include/server/mir/shell/surface.h 2014-03-06 06:05:17 +0000
1846+++ include/server/mir/shell/surface.h 2014-04-07 13:29:13 +0000
1847@@ -50,10 +50,8 @@
1848
1849 virtual void allow_framedropping(bool) = 0;
1850
1851- virtual void raise(std::shared_ptr<scene::SurfaceRanker> const& controller) = 0;
1852-
1853 virtual void resize(geometry::Size const& size) = 0;
1854- virtual void set_rotation(float degrees, glm::vec3 const& axis) = 0;
1855+ virtual void set_transformation(glm::mat4 const& t) = 0;
1856
1857 virtual float alpha() const = 0;
1858 virtual void set_alpha(float alpha) = 0;
1859
1860=== modified file 'include/server/mir/shell/surface_factory.h'
1861--- include/server/mir/shell/surface_factory.h 2013-08-28 03:41:48 +0000
1862+++ include/server/mir/shell/surface_factory.h 2014-04-07 13:29:13 +0000
1863@@ -1,5 +1,5 @@
1864 /*
1865- * Copyright © 2012 Canonical Ltd.
1866+ * Copyright © 2012-2014 Canonical Ltd.
1867 *
1868 * This program is free software: you can redistribute it and/or modify it
1869 * under the terms of the GNU General Public License version 3,
1870@@ -19,15 +19,12 @@
1871 #ifndef MIR_SHELL_SURFACE_FACTORY_H_
1872 #define MIR_SHELL_SURFACE_FACTORY_H_
1873
1874-#include "mir/frontend/surface_id.h"
1875 #include <memory>
1876
1877 namespace mir
1878 {
1879-namespace frontend
1880-{
1881-class EventSink;
1882-}
1883+namespace scene { class SurfaceObserver; }
1884+
1885 namespace shell
1886 {
1887 class Session;
1888@@ -40,8 +37,9 @@
1889 virtual std::shared_ptr<Surface> create_surface(
1890 Session* session,
1891 SurfaceCreationParameters const& params,
1892- frontend::SurfaceId id,
1893- std::shared_ptr<frontend::EventSink> const& sink) = 0;
1894+ std::shared_ptr<scene::SurfaceObserver> const& observer) = 0;
1895+
1896+ virtual void destroy_surface(std::shared_ptr<Surface> const& surface) = 0;
1897
1898 protected:
1899 virtual ~SurfaceFactory() {}
1900
1901=== added file 'include/shared/mir/geometry/length.h'
1902--- include/shared/mir/geometry/length.h 1970-01-01 00:00:00 +0000
1903+++ include/shared/mir/geometry/length.h 2014-04-07 13:29:13 +0000
1904@@ -0,0 +1,102 @@
1905+/*
1906+ * Copyright © 2014 Canonical Ltd.
1907+ *
1908+ * This program is free software: you can redistribute it and/or modify it
1909+ * under the terms of the GNU Lesser General Public License version 3,
1910+ * as published by the Free Software Foundation.
1911+ *
1912+ * This program is distributed in the hope that it will be useful,
1913+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
1914+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
1915+ * GNU Lesser General Public License for more details.
1916+ *
1917+ * You should have received a copy of the GNU Lesser General Public License
1918+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
1919+ *
1920+ * Authored by: Daniel van Vugt <daniel.van.vugt@canonical.com>
1921+ */
1922+
1923+#ifndef MIR_GEOMETRY_LENGTH_H_
1924+#define MIR_GEOMETRY_LENGTH_H_
1925+
1926+namespace mir
1927+{
1928+namespace geometry
1929+{
1930+
1931+/// Length represents a physical length in the real world. The number of pixels
1932+/// this equates to can then be calculated based on a given DPI.
1933+class Length
1934+{
1935+public:
1936+ enum Units
1937+ {
1938+ micrometres = 1,
1939+ millimetres = 1000,
1940+ centimetres = 10000,
1941+ inches = 25400
1942+ };
1943+
1944+ Length() : magnitude(0) {}
1945+ Length(Length const&) = default;
1946+ Length& operator=(Length const&) = default;
1947+ Length(float mag, Units units) : magnitude(mag * units) {}
1948+
1949+ float as(Units units) const
1950+ {
1951+ return static_cast<float>(magnitude) / units;
1952+ }
1953+
1954+ float as_pixels(float dpi) const
1955+ {
1956+ return as(inches) * dpi;
1957+ }
1958+
1959+ bool operator==(Length const& rhs) const
1960+ {
1961+ return magnitude == rhs.magnitude;
1962+ }
1963+
1964+ bool operator!=(Length const& rhs) const
1965+ {
1966+ return magnitude != rhs.magnitude;
1967+ }
1968+
1969+private:
1970+ float magnitude;
1971+};
1972+
1973+inline Length operator"" _mm(long double mag)
1974+{
1975+ return Length(mag, Length::millimetres);
1976+}
1977+
1978+inline Length operator"" _mm(unsigned long long mag)
1979+{
1980+ return Length(mag, Length::millimetres);
1981+}
1982+
1983+inline Length operator"" _cm(long double mag)
1984+{
1985+ return Length(mag, Length::centimetres);
1986+}
1987+
1988+inline Length operator"" _cm(unsigned long long mag)
1989+{
1990+ return Length(mag, Length::centimetres);
1991+}
1992+
1993+inline Length operator"" _in(long double mag)
1994+{
1995+ return Length(mag, Length::inches);
1996+}
1997+
1998+inline Length operator"" _in(unsigned long long mag)
1999+{
2000+ return Length(mag, Length::inches);
2001+}
2002+
2003+} // namespace geometry
2004+} // namespace mir
2005+
2006+#endif // MIR_GEOMETRY_LENGTH_H_
2007
2008=== modified file 'include/test/mir_test_doubles/fake_renderable.h'
2009--- include/test/mir_test_doubles/fake_renderable.h 2014-03-17 07:35:22 +0000
2010+++ include/test/mir_test_doubles/fake_renderable.h 2014-04-07 13:29:13 +0000
2011@@ -42,7 +42,7 @@
2012 : rect{{x, y}, {width, height}},
2013 opacity(opacity),
2014 rectangular(rectangular),
2015- visible(visible),
2016+ visible_(visible),
2017 posted(posted)
2018 {
2019 }
2020@@ -57,9 +57,9 @@
2021 return glm::mat4();
2022 }
2023
2024- bool should_be_rendered_in(const mir::geometry::Rectangle &r) const override
2025+ bool visible() const override
2026 {
2027- return visible && posted && rect.overlaps(r);
2028+ return visible_ && posted;
2029 }
2030
2031 bool shaped() const override
2032@@ -72,7 +72,7 @@
2033 buf = b;
2034 }
2035
2036- std::shared_ptr<graphics::Buffer> buffer(unsigned long) const override
2037+ std::shared_ptr<graphics::Buffer> buffer(void const*) const override
2038 {
2039 return buf;
2040 }
2041@@ -97,7 +97,7 @@
2042 mir::geometry::Rectangle rect;
2043 float opacity;
2044 bool rectangular;
2045- bool visible;
2046+ bool visible_;
2047 bool posted;
2048 };
2049
2050
2051=== modified file 'include/test/mir_test_doubles/mock_buffer_bundle.h'
2052--- include/test/mir_test_doubles/mock_buffer_bundle.h 2014-03-07 03:15:55 +0000
2053+++ include/test/mir_test_doubles/mock_buffer_bundle.h 2014-04-07 13:29:13 +0000
2054@@ -39,7 +39,7 @@
2055
2056 MOCK_METHOD1(client_acquire, void(std::function<void(graphics::Buffer*)>));
2057 MOCK_METHOD1(client_release, void(graphics::Buffer*));
2058- MOCK_METHOD1(compositor_acquire, std::shared_ptr<graphics::Buffer>(unsigned long));
2059+ MOCK_METHOD1(compositor_acquire, std::shared_ptr<graphics::Buffer>(void const*));
2060 MOCK_METHOD1(compositor_release, void(std::shared_ptr<graphics::Buffer> const&));
2061 MOCK_METHOD0(snapshot_acquire, std::shared_ptr<graphics::Buffer>());
2062 MOCK_METHOD1(snapshot_release, void(std::shared_ptr<graphics::Buffer> const&));
2063
2064=== modified file 'include/test/mir_test_doubles/mock_buffer_stream.h'
2065--- include/test/mir_test_doubles/mock_buffer_stream.h 2014-03-07 03:15:55 +0000
2066+++ include/test/mir_test_doubles/mock_buffer_stream.h 2014-04-07 13:29:13 +0000
2067@@ -33,7 +33,7 @@
2068 {
2069 MOCK_METHOD2(swap_client_buffers, void(graphics::Buffer*, std::function<void(graphics::Buffer*)> completee));
2070 MOCK_METHOD1(lock_compositor_buffer,
2071- std::shared_ptr<graphics::Buffer>(unsigned long));
2072+ std::shared_ptr<graphics::Buffer>(void const*));
2073 MOCK_METHOD0(lock_snapshot_buffer, std::shared_ptr<graphics::Buffer>());
2074
2075 MOCK_METHOD0(get_stream_pixel_format, MirPixelFormat());
2076
2077=== modified file 'include/test/mir_test_doubles/mock_display_buffer.h'
2078--- include/test/mir_test_doubles/mock_display_buffer.h 2014-03-06 06:05:17 +0000
2079+++ include/test/mir_test_doubles/mock_display_buffer.h 2014-04-07 13:29:13 +0000
2080@@ -46,7 +46,7 @@
2081 MOCK_METHOD0(release_current, void());
2082 MOCK_METHOD0(post_update, void());
2083 MOCK_CONST_METHOD0(can_bypass, bool());
2084- MOCK_METHOD2(render_and_post_update, void(std::list<std::shared_ptr<graphics::Renderable>> const&,
2085+ MOCK_METHOD2(render_and_post_update, void(graphics::RenderableList const&,
2086 std::function<void(graphics::Renderable const&)> const&));
2087 MOCK_CONST_METHOD0(orientation, MirOrientation());
2088 };
2089
2090=== modified file 'include/test/mir_test_doubles/mock_display_changer.h'
2091--- include/test/mir_test_doubles/mock_display_changer.h 2013-09-17 20:03:16 +0000
2092+++ include/test/mir_test_doubles/mock_display_changer.h 2014-04-07 13:29:13 +0000
2093@@ -35,7 +35,6 @@
2094 MOCK_METHOD0(active_configuration, std::shared_ptr<graphics::DisplayConfiguration>());
2095 MOCK_METHOD2(configure,
2096 void(std::shared_ptr<frontend::Session> const&, std::shared_ptr<graphics::DisplayConfiguration> const&));
2097- MOCK_METHOD1(ensure_display_powered, void(std::shared_ptr<frontend::Session> const&));
2098 };
2099
2100 }
2101
2102=== modified file 'include/test/mir_test_doubles/mock_display_device.h'
2103--- include/test/mir_test_doubles/mock_display_device.h 2014-03-11 13:44:57 +0000
2104+++ include/test/mir_test_doubles/mock_display_device.h 2014-04-07 13:29:13 +0000
2105@@ -38,7 +38,7 @@
2106 MOCK_METHOD1(render_gl, void(graphics::android::SwappingGLContext const&));
2107 MOCK_METHOD3(render_gl_and_overlays, void(
2108 graphics::android::SwappingGLContext const&,
2109- std::list<std::shared_ptr<graphics::Renderable>> const&,
2110+ graphics::RenderableList const&,
2111 std::function<void(graphics::Renderable const&)> const&));
2112 MOCK_METHOD1(post, void(graphics::Buffer const&));
2113 MOCK_CONST_METHOD1(apply_orientation, bool(MirOrientation));
2114
2115=== modified file 'include/test/mir_test_doubles/mock_egl.h'
2116--- include/test/mir_test_doubles/mock_egl.h 2014-03-06 06:05:17 +0000
2117+++ include/test/mir_test_doubles/mock_egl.h 2014-04-07 13:29:13 +0000
2118@@ -53,6 +53,33 @@
2119 return false;
2120 }
2121
2122+MATCHER_P2(EGLConfigContainsAttrib, attrib, value, "")
2123+{
2124+ bool attrib_position = true;
2125+ bool attrib_found = false;
2126+
2127+ while (!attrib_position || *arg != EGL_NONE)
2128+ {
2129+ if (attrib_position && *arg == attrib)
2130+ {
2131+ attrib_found = true;
2132+ }
2133+ else if (!attrib_position)
2134+ {
2135+ if (attrib_found && *arg == value)
2136+ {
2137+ return true;
2138+ }
2139+
2140+ attrib_found = false;
2141+ }
2142+ attrib_position = !attrib_position;
2143+ ++arg;
2144+ }
2145+
2146+ return false;
2147+}
2148+
2149 class MockEGL
2150 {
2151 public:
2152
2153=== added file 'include/test/mir_test_doubles/mock_gl_config.h'
2154--- include/test/mir_test_doubles/mock_gl_config.h 1970-01-01 00:00:00 +0000
2155+++ include/test/mir_test_doubles/mock_gl_config.h 2014-04-07 13:29:13 +0000
2156@@ -0,0 +1,43 @@
2157+/*
2158+ * Copyright © 2014 Canonical Ltd.
2159+ *
2160+ * This program is free software: you can redistribute it and/or modify it
2161+ * under the terms of the GNU General Public License version 3,
2162+ * as published by the Free Software Foundation.
2163+ *
2164+ * This program is distributed in the hope that it will be useful,
2165+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
2166+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
2167+ * GNU General Public License for more details.
2168+ *
2169+ * You should have received a copy of the GNU General Public License
2170+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
2171+ *
2172+ * Authored by: Alexandros Frantzis <alexandros.frantzis@canonical.com>
2173+ */
2174+
2175+#ifndef MIR_TEST_DOUBLES_MOCK_GL_CONFIG_H_
2176+#define MIR_TEST_DOUBLES_MOCK_GL_CONFIG_H_
2177+
2178+#include "mir/graphics/gl_config.h"
2179+
2180+#include <gmock/gmock.h>
2181+
2182+namespace mir
2183+{
2184+namespace test
2185+{
2186+namespace doubles
2187+{
2188+
2189+struct MockGLConfig : public graphics::GLConfig
2190+{
2191+ MOCK_CONST_METHOD0(depth_buffer_bits, int());
2192+ MOCK_CONST_METHOD0(stencil_buffer_bits, int());
2193+};
2194+
2195+}
2196+}
2197+}
2198+
2199+#endif /* MIR_TEST_DOUBLES_MOCK_GL_CONFIG_H_ */
2200
2201=== modified file 'include/test/mir_test_doubles/mock_hwc_composer_device_1.h'
2202--- include/test/mir_test_doubles/mock_hwc_composer_device_1.h 2014-03-06 06:05:17 +0000
2203+++ include/test/mir_test_doubles/mock_hwc_composer_device_1.h 2014-04-07 13:29:13 +0000
2204@@ -21,8 +21,6 @@
2205
2206 #include <hardware/hwcomposer.h>
2207 #include <gmock/gmock.h>
2208-#include <vector>
2209-#include <memory>
2210
2211 namespace mir
2212 {
2213@@ -37,16 +35,6 @@
2214 MockHWCComposerDevice1()
2215 {
2216 using namespace testing;
2217-
2218- primary_prepare = false;
2219- primary_set = false;
2220- external_prepare = false;
2221- external_set = false;
2222- virtual_prepare = false;
2223- virtual_set = false;
2224- fb_fence = -1;
2225- retire_fence = -1;
2226-
2227 common.version = HWC_DEVICE_API_VERSION_1_1;
2228
2229 registerProcs = hook_registerProcs;
2230@@ -56,91 +44,6 @@
2231 blank = hook_blank;
2232 getDisplayConfigs = hook_getDisplayConfigs;
2233 getDisplayAttributes = hook_getDisplayAttributes;
2234-
2235- ON_CALL(*this, set_interface(_,_,_))
2236- .WillByDefault(Invoke(this, &MockHWCComposerDevice1::save_last_set_arguments));
2237- ON_CALL(*this, prepare_interface(_,_,_))
2238- .WillByDefault(Invoke(this, &MockHWCComposerDevice1::save_last_prepare_arguments));
2239- }
2240-
2241- int save_args(hwc_display_contents_1_t* out, hwc_display_contents_1_t** in)
2242- {
2243- if ((nullptr == in) || (nullptr == *in))
2244- return -1;
2245-
2246- hwc_display_contents_1_t* primary_display = *in;
2247- memcpy(out, primary_display, sizeof(hwc_display_contents_1_t));
2248- return 0;
2249- }
2250-
2251- void hwc_set_return_fence(int fence)
2252- {
2253- fb_fence = fence;
2254- }
2255-
2256- void hwc_set_retire_fence(int fence)
2257- {
2258- retire_fence = fence;
2259- }
2260-
2261- int save_last_prepare_arguments(struct hwc_composer_device_1 *, size_t size, hwc_display_contents_1_t** displays)
2262- {
2263- if ((size == 0) || (!displays))
2264- return -1;
2265-
2266- switch (size)
2267- {
2268- case 3:
2269- virtual_prepare = (!!displays[2]);
2270- case 2:
2271- external_prepare = (!!displays[1]);
2272- case 1:
2273- primary_prepare = (!!displays[0]);
2274- for(auto i = 0u; i < displays[0]->numHwLayers; i++)
2275- {
2276- prepare_layerlist.push_back(displays[0]->hwLayers[i]);
2277- prepare_layerlist.back().visibleRegionScreen = {0, nullptr};
2278- }
2279- save_args(&display0_prepare_content, displays);
2280- default:
2281- break;
2282- }
2283- return 0;
2284- }
2285-
2286- int save_last_set_arguments(
2287- struct hwc_composer_device_1 *, size_t size, hwc_display_contents_1_t** displays)
2288- {
2289-
2290- if ((size == 0) || (!displays))
2291- return -1;
2292-
2293- switch (size)
2294- {
2295- case 3:
2296- virtual_set = (!!displays[2]);
2297- case 2:
2298- external_set = (!!displays[1]);
2299- case 1:
2300- primary_set = (!!displays[0]);
2301- for(auto i = 0u; i < displays[0]->numHwLayers; i++)
2302- {
2303- set_layerlist.push_back(displays[0]->hwLayers[i]);
2304- set_layerlist.back().visibleRegionScreen = {0, nullptr};
2305- }
2306-
2307- save_args(&display0_set_content, displays);
2308-
2309- if (displays[0]->numHwLayers >= 2)
2310- {
2311- displays[0]->hwLayers[1].releaseFenceFd = fb_fence;
2312- displays[0]->retireFenceFd = retire_fence;
2313- }
2314-
2315- default:
2316- break;
2317- }
2318- return 0;
2319 }
2320
2321 static void hook_registerProcs(struct hwc_composer_device_1* mock_hwc, hwc_procs_t const* procs)
2322@@ -188,14 +91,6 @@
2323 MOCK_METHOD3(blank_interface, int(struct hwc_composer_device_1 *, int, int));
2324 MOCK_METHOD4(getDisplayConfigs_interface, int(struct hwc_composer_device_1*, int, uint32_t*, size_t*));
2325 MOCK_METHOD5(getDisplayAttributes_interface, int(struct hwc_composer_device_1*, int, uint32_t, const uint32_t*, int32_t*));
2326-
2327- bool primary_prepare, primary_set, external_prepare, external_set, virtual_prepare, virtual_set;
2328- hwc_display_contents_1_t display0_set_content;
2329- std::vector<hwc_layer_1> set_layerlist;
2330- std::vector<hwc_layer_1> prepare_layerlist;
2331- hwc_display_contents_1_t display0_prepare_content;
2332- int fb_fence;
2333- int retire_fence;
2334 };
2335
2336 }
2337
2338=== added file 'include/test/mir_test_doubles/mock_hwc_device_wrapper.h'
2339--- include/test/mir_test_doubles/mock_hwc_device_wrapper.h 1970-01-01 00:00:00 +0000
2340+++ include/test/mir_test_doubles/mock_hwc_device_wrapper.h 2014-04-07 13:29:13 +0000
2341@@ -0,0 +1,42 @@
2342+/*
2343+ * Copyright © 2014 Canonical Ltd.
2344+ *
2345+ * This program is free software: you can redistribute it and/or modify it
2346+ * under the terms of the GNU General Public License version 3,
2347+ * as published by the Free Software Foundation.
2348+ *
2349+ * This program is distributed in the hope that it will be useful,
2350+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
2351+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
2352+ * GNU General Public License for more details.
2353+ *
2354+ * You should have received a copy of the GNU General Public License
2355+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
2356+ *
2357+ * Authored by: Kevin DuBois <kevin.dubois@canonical.com>
2358+ */
2359+
2360+#ifndef MIR_TEST_DOUBLES_MOCK_HWC_DEVICE_WRAPPER_H_
2361+#define MIR_TEST_DOUBLES_MOCK_HWC_DEVICE_WRAPPER_H_
2362+
2363+#include "src/platform/graphics/android/hwc_wrapper.h"
2364+
2365+#include <gmock/gmock.h>
2366+
2367+namespace mir
2368+{
2369+namespace test
2370+{
2371+namespace doubles
2372+{
2373+
2374+struct MockHWCDeviceWrapper : public graphics::android::HwcWrapper
2375+{
2376+ MOCK_CONST_METHOD1(prepare, void(hwc_display_contents_1_t&));
2377+ MOCK_CONST_METHOD1(set, void(hwc_display_contents_1_t&));
2378+};
2379+
2380+}
2381+}
2382+}
2383+#endif /* MIR_TEST_DOUBLES_MOCK_HWC_DEVICE_WRAPPER_H_ */
2384
2385=== modified file 'include/test/mir_test_doubles/mock_input_surface.h'
2386--- include/test/mir_test_doubles/mock_input_surface.h 2014-03-06 06:05:17 +0000
2387+++ include/test/mir_test_doubles/mock_input_surface.h 2014-04-07 13:29:13 +0000
2388@@ -43,12 +43,12 @@
2389 Return(geometry::Size{}));
2390 static std::string n;
2391 ON_CALL(*this, name())
2392- .WillByDefault(testing::ReturnRef(n));
2393+ .WillByDefault(testing::Return(n));
2394 }
2395 ~MockInputSurface() noexcept {}
2396 MOCK_CONST_METHOD0(top_left, geometry::Point());
2397 MOCK_CONST_METHOD0(size, geometry::Size());
2398- MOCK_CONST_METHOD0(name, std::string const&());
2399+ MOCK_CONST_METHOD0(name, std::string());
2400 MOCK_CONST_METHOD1(contains, bool(geometry::Point const&));
2401 };
2402
2403
2404=== modified file 'include/test/mir_test_doubles/mock_renderable.h'
2405--- include/test/mir_test_doubles/mock_renderable.h 2014-03-17 07:35:22 +0000
2406+++ include/test/mir_test_doubles/mock_renderable.h 2014-04-07 13:29:13 +0000
2407@@ -37,15 +37,24 @@
2408 .WillByDefault(testing::Return(geometry::Rectangle{{},{}}));
2409 ON_CALL(*this, buffer(testing::_))
2410 .WillByDefault(testing::Return(std::make_shared<StubBuffer>()));
2411+ ON_CALL(*this, buffers_ready_for_compositor())
2412+ .WillByDefault(testing::Return(1));
2413+ ON_CALL(*this, alpha())
2414+ .WillByDefault(testing::Return(1.0f));
2415+ ON_CALL(*this, transformation())
2416+ .WillByDefault(testing::Return(glm::mat4{}));
2417+ ON_CALL(*this, visible())
2418+ .WillByDefault(testing::Return(true));
2419 }
2420- MOCK_CONST_METHOD1(buffer, std::shared_ptr<graphics::Buffer>(unsigned long));
2421+
2422+ MOCK_CONST_METHOD1(buffer, std::shared_ptr<graphics::Buffer>(void const*));
2423 MOCK_CONST_METHOD0(alpha_enabled, bool());
2424 MOCK_CONST_METHOD0(screen_position, geometry::Rectangle());
2425 MOCK_CONST_METHOD0(alpha, float());
2426 MOCK_CONST_METHOD0(transformation, glm::mat4());
2427- MOCK_CONST_METHOD1(should_be_rendered_in, bool(geometry::Rectangle const& rect));
2428+ MOCK_CONST_METHOD0(visible, bool());
2429 MOCK_CONST_METHOD0(shaped, bool());
2430- int buffers_ready_for_compositor() const override { return 1; }
2431+ MOCK_CONST_METHOD0(buffers_ready_for_compositor, int());
2432 };
2433 }
2434 }
2435
2436=== modified file 'include/test/mir_test_doubles/mock_scene.h'
2437--- include/test/mir_test_doubles/mock_scene.h 2014-03-13 09:22:13 +0000
2438+++ include/test/mir_test_doubles/mock_scene.h 2014-04-07 13:29:13 +0000
2439@@ -32,10 +32,14 @@
2440 class MockScene : public compositor::Scene
2441 {
2442 public:
2443+ MockScene()
2444+ {
2445+ ON_CALL(*this, generate_renderable_list())
2446+ .WillByDefault(testing::Return(graphics::RenderableList{}));
2447+ }
2448+ MOCK_CONST_METHOD0(generate_renderable_list, graphics::RenderableList());
2449 MOCK_METHOD2(for_each_if, void(compositor::FilterForScene&,
2450 compositor::OperatorForScene&));
2451- MOCK_METHOD2(reverse_for_each_if, void(compositor::FilterForScene&,
2452- compositor::OperatorForScene&));
2453 MOCK_METHOD1(set_change_callback, void(std::function<void()> const&));
2454 MOCK_METHOD0(lock, void());
2455 MOCK_METHOD0(unlock, void());
2456
2457=== modified file 'include/test/mir_test_doubles/mock_surface.h'
2458--- include/test/mir_test_doubles/mock_surface.h 2014-03-06 06:05:17 +0000
2459+++ include/test/mir_test_doubles/mock_surface.h 2014-04-07 13:29:13 +0000
2460@@ -1,5 +1,5 @@
2461 /*
2462- * Copyright © 2013 Canonical Ltd.
2463+ * Copyright © 2013-2014 Canonical Ltd.
2464 *
2465 * This program is free software: you can redistribute it and/or modify it
2466 * under the terms of the GNU General Public License version 3,
2467@@ -19,16 +19,11 @@
2468 #ifndef MIR_TEST_DOUBLES_MOCK_SURFACE_H_
2469 #define MIR_TEST_DOUBLES_MOCK_SURFACE_H_
2470
2471-#include "src/server/scene/surface_impl.h"
2472-
2473-#include "mir/shell/surface_creation_parameters.h"
2474-#include "null_event_sink.h"
2475-#include "null_surface_configurator.h"
2476+#include "src/server/scene/basic_surface.h"
2477+#include "src/server/report/null_report_factory.h"
2478
2479 #include <gmock/gmock.h>
2480
2481-#include <memory>
2482-
2483 namespace mir
2484 {
2485 namespace test
2486@@ -36,10 +31,17 @@
2487 namespace doubles
2488 {
2489
2490-struct MockSurface : public scene::SurfaceImpl
2491+struct MockSurface : public scene::BasicSurface
2492 {
2493- MockSurface(std::shared_ptr<scene::SurfaceBuilder> const& builder) :
2494- scene::SurfaceImpl(builder, std::make_shared<NullSurfaceConfigurator>(), shell::a_surface(), frontend::SurfaceId{}, std::make_shared<NullEventSink>())
2495+ MockSurface() :
2496+ scene::BasicSurface(
2497+ {},
2498+ {{},{}},
2499+ true,
2500+ {},
2501+ {},
2502+ {},
2503+ mir::report::null_scene_report())
2504 {
2505 }
2506
2507@@ -53,7 +55,6 @@
2508 MOCK_METHOD0(force_requests_to_complete, void());
2509 MOCK_METHOD0(advance_client_buffer, std::shared_ptr<graphics::Buffer>());
2510
2511- MOCK_CONST_METHOD0(name, std::string());
2512 MOCK_CONST_METHOD0(size, geometry::Size());
2513 MOCK_CONST_METHOD0(pixel_format, MirPixelFormat());
2514
2515@@ -62,6 +63,7 @@
2516
2517 MOCK_METHOD2(configure, int(MirSurfaceAttrib, int));
2518 MOCK_METHOD1(take_input_focus, void(std::shared_ptr<shell::InputTargeter> const&));
2519+ MOCK_METHOD1(add_observer, void(std::shared_ptr<scene::SurfaceObserver> const&));
2520 };
2521
2522 }
2523
2524=== modified file 'include/test/mir_test_doubles/mock_surface_configurator.h'
2525--- include/test/mir_test_doubles/mock_surface_configurator.h 2013-07-31 23:09:53 +0000
2526+++ include/test/mir_test_doubles/mock_surface_configurator.h 2014-04-07 13:29:13 +0000
2527@@ -19,7 +19,7 @@
2528 #ifndef MIR_TEST_DOUBLES_MOCK_SURFACE_CONFIGURATOR_H_
2529 #define MIR_TEST_DOUBLES_MOCK_SURFACE_CONFIGURATOR_H_
2530
2531-#include "mir/shell/surface_configurator.h"
2532+#include "mir/scene/surface_configurator.h"
2533
2534 #include <gmock/gmock.h>
2535
2536@@ -30,10 +30,10 @@
2537 namespace doubles
2538 {
2539
2540-struct MockSurfaceConfigurator : public shell::SurfaceConfigurator
2541+struct MockSurfaceConfigurator : public scene::SurfaceConfigurator
2542 {
2543- MOCK_METHOD3(select_attribute_value, int(shell::Surface const&, MirSurfaceAttrib, int));
2544- MOCK_METHOD3(attribute_set, void(shell::Surface const&, MirSurfaceAttrib, int));
2545+ MOCK_METHOD3(select_attribute_value, int(scene::Surface const&, MirSurfaceAttrib, int));
2546+ MOCK_METHOD3(attribute_set, void(scene::Surface const&, MirSurfaceAttrib, int));
2547 };
2548
2549 }
2550
2551=== modified file 'include/test/mir_test_doubles/mock_surface_factory.h'
2552--- include/test/mir_test_doubles/mock_surface_factory.h 2013-08-28 03:41:48 +0000
2553+++ include/test/mir_test_doubles/mock_surface_factory.h 2014-04-07 13:29:13 +0000
2554@@ -33,11 +33,12 @@
2555
2556 struct MockSurfaceFactory : public shell::SurfaceFactory
2557 {
2558- MOCK_METHOD4(create_surface, std::shared_ptr<shell::Surface>(
2559+ MOCK_METHOD3(create_surface, std::shared_ptr<shell::Surface>(
2560 shell::Session*,
2561 const shell::SurfaceCreationParameters&,
2562- frontend::SurfaceId,
2563- std::shared_ptr<frontend::EventSink> const&));
2564+ std::shared_ptr<scene::SurfaceObserver> const&));
2565+
2566+ void destroy_surface(std::shared_ptr<shell::Surface> const& /*surface*/) override {}
2567 };
2568
2569 }
2570
2571=== modified file 'include/test/mir_test_doubles/mock_surface_ranker.h'
2572--- include/test/mir_test_doubles/mock_surface_ranker.h 2014-03-06 06:05:17 +0000
2573+++ include/test/mir_test_doubles/mock_surface_ranker.h 2014-04-07 13:29:13 +0000
2574@@ -20,7 +20,7 @@
2575 #ifndef MIR_TEST_DOUBLES_MOCK_SURFACE_RANKER_H_
2576 #define MIR_TEST_DOUBLES_MOCK_SURFACE_RANKER_H_
2577
2578-#include "src/server/scene/surface_ranker.h"
2579+#include "mir/scene/surface_ranker.h"
2580
2581 #include <gmock/gmock.h>
2582
2583@@ -33,7 +33,7 @@
2584
2585 struct MockSurfaceRanker : public scene::SurfaceRanker
2586 {
2587- MOCK_METHOD1(raise, void(std::weak_ptr<scene::BasicSurface> const&));
2588+ MOCK_METHOD1(raise, void(std::weak_ptr<scene::Surface> const&));
2589 };
2590
2591 }
2592
2593=== modified file 'include/test/mir_test_doubles/null_display_buffer.h'
2594--- include/test/mir_test_doubles/null_display_buffer.h 2014-03-06 06:05:17 +0000
2595+++ include/test/mir_test_doubles/null_display_buffer.h 2014-04-07 13:29:13 +0000
2596@@ -37,7 +37,7 @@
2597 void post_update() {}
2598 bool can_bypass() const override { return false; }
2599 void render_and_post_update(
2600- std::list<std::shared_ptr<graphics::Renderable>> const&,
2601+ graphics::RenderableList const&,
2602 std::function<void(graphics::Renderable const&)> const&) {}
2603 MirOrientation orientation() const override { return mir_orientation_normal; }
2604 };
2605
2606=== modified file 'include/test/mir_test_doubles/null_display_changer.h'
2607--- include/test/mir_test_doubles/null_display_changer.h 2013-09-17 20:03:16 +0000
2608+++ include/test/mir_test_doubles/null_display_changer.h 2014-04-07 13:29:13 +0000
2609@@ -39,9 +39,6 @@
2610 virtual void configure(std::shared_ptr<frontend::Session> const&, std::shared_ptr<graphics::DisplayConfiguration> const&)
2611 {
2612 }
2613- virtual void ensure_display_powered(std::shared_ptr<frontend::Session> const&)
2614- {
2615- }
2616 };
2617 }
2618 }
2619
2620=== modified file 'include/test/mir_test_doubles/null_platform.h'
2621--- include/test/mir_test_doubles/null_platform.h 2014-03-06 06:05:17 +0000
2622+++ include/test/mir_test_doubles/null_platform.h 2014-04-07 13:29:13 +0000
2623@@ -39,7 +39,8 @@
2624 }
2625
2626 std::shared_ptr<graphics::Display> create_display(
2627- std::shared_ptr<graphics::DisplayConfigurationPolicy> const&)
2628+ std::shared_ptr<graphics::DisplayConfigurationPolicy> const&,
2629+ std::shared_ptr<graphics::GLConfig> const&)
2630 {
2631 return std::make_shared<NullDisplay>();
2632 }
2633
2634=== modified file 'include/test/mir_test_doubles/null_surface_configurator.h'
2635--- include/test/mir_test_doubles/null_surface_configurator.h 2013-07-29 22:55:20 +0000
2636+++ include/test/mir_test_doubles/null_surface_configurator.h 2014-04-07 13:29:13 +0000
2637@@ -19,7 +19,7 @@
2638 #ifndef MIR_TEST_DOUBLES_NULL_SURFACE_CONFIGURATOR_H_
2639 #define MIR_TEST_DOUBLES_NULL_SURFACE_CONFIGURATOR_H_
2640
2641-#include "mir/shell/surface_configurator.h"
2642+#include "mir/scene/surface_configurator.h"
2643
2644 namespace mir
2645 {
2646@@ -28,14 +28,14 @@
2647 namespace doubles
2648 {
2649
2650-struct NullSurfaceConfigurator : public shell::SurfaceConfigurator
2651+struct NullSurfaceConfigurator : public scene::SurfaceConfigurator
2652 {
2653- int select_attribute_value(shell::Surface const&,
2654+ int select_attribute_value(scene::Surface const&,
2655 MirSurfaceAttrib, int requested_value)
2656 {
2657 return requested_value;
2658 }
2659- void attribute_set(shell::Surface const&,
2660+ void attribute_set(scene::Surface const&,
2661 MirSurfaceAttrib, int)
2662 {
2663 }
2664
2665=== modified file 'include/test/mir_test_doubles/stub_buffer_stream.h'
2666--- include/test/mir_test_doubles/stub_buffer_stream.h 2014-03-07 03:15:55 +0000
2667+++ include/test/mir_test_doubles/stub_buffer_stream.h 2014-04-07 13:29:13 +0000
2668@@ -40,7 +40,7 @@
2669 {
2670 complete(&stub_client_buffer);
2671 }
2672- std::shared_ptr<graphics::Buffer> lock_compositor_buffer(unsigned long) override
2673+ std::shared_ptr<graphics::Buffer> lock_compositor_buffer(void const*) override
2674 {
2675 return stub_compositor_buffer;
2676 }
2677
2678=== modified file 'include/test/mir_test_doubles/stub_display_builder.h'
2679--- include/test/mir_test_doubles/stub_display_builder.h 2014-03-06 06:05:17 +0000
2680+++ include/test/mir_test_doubles/stub_display_builder.h 2014-04-07 13:29:13 +0000
2681@@ -43,7 +43,7 @@
2682 void post_update() {}
2683 bool can_bypass() const override { return false; }
2684 void render_and_post_update(
2685- std::list<std::shared_ptr<graphics::Renderable>> const&,
2686+ graphics::RenderableList const&,
2687 std::function<void(graphics::Renderable const&)> const&) {}
2688 MirOrientation orientation() const override { return mir_orientation_normal; }
2689 void configure(graphics::DisplayConfigurationOutput const&) {}
2690
2691=== modified file 'include/test/mir_test_doubles/stub_display_device.h'
2692--- include/test/mir_test_doubles/stub_display_device.h 2014-03-11 13:44:57 +0000
2693+++ include/test/mir_test_doubles/stub_display_device.h 2014-04-07 13:29:13 +0000
2694@@ -40,7 +40,7 @@
2695 }
2696 void render_gl_and_overlays(
2697 graphics::android::SwappingGLContext const&,
2698- std::list<std::shared_ptr<graphics::Renderable>> const&,
2699+ graphics::RenderableList const&,
2700 std::function<void(graphics::Renderable const&)> const&)
2701 {
2702 }
2703
2704=== added file 'include/test/mir_test_doubles/stub_gl_config.h'
2705--- include/test/mir_test_doubles/stub_gl_config.h 1970-01-01 00:00:00 +0000
2706+++ include/test/mir_test_doubles/stub_gl_config.h 2014-04-07 13:29:13 +0000
2707@@ -0,0 +1,43 @@
2708+/*
2709+ * Copyright © 2014 Canonical Ltd.
2710+ *
2711+ * This program is free software: you can redistribute it and/or modify it
2712+ * under the terms of the GNU General Public License version 3,
2713+ * as published by the Free Software Foundation.
2714+ *
2715+ * This program is distributed in the hope that it will be useful,
2716+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
2717+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
2718+ * GNU General Public License for more details.
2719+ *
2720+ * You should have received a copy of the GNU General Public License
2721+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
2722+ *
2723+ * Authored by: Alexandros Frantzis <alexandros.frantzis@canonical.com>
2724+ */
2725+
2726+#ifndef MIR_TEST_DOUBLES_STUB_GL_CONFIG_H_
2727+#define MIR_TEST_DOUBLES_STUB_GL_CONFIG_H_
2728+
2729+#include "mir/graphics/gl_config.h"
2730+
2731+#include <gmock/gmock.h>
2732+
2733+namespace mir
2734+{
2735+namespace test
2736+{
2737+namespace doubles
2738+{
2739+
2740+struct StubGLConfig : public graphics::GLConfig
2741+{
2742+ int depth_buffer_bits() const override { return 0; }
2743+ int stencil_buffer_bits() const override { return 0; }
2744+};
2745+
2746+}
2747+}
2748+}
2749+
2750+#endif /* MIR_TEST_DOUBLES_STUB_GL_CONFIG_H_ */
2751
2752=== modified file 'include/test/mir_test_doubles/stub_ipc_factory.h'
2753--- include/test/mir_test_doubles/stub_ipc_factory.h 2014-03-06 06:05:17 +0000
2754+++ include/test/mir_test_doubles/stub_ipc_factory.h 2014-04-07 13:29:13 +0000
2755@@ -41,7 +41,7 @@
2756 }
2757
2758 std::shared_ptr<protobuf::DisplayServer> make_ipc_server(
2759- pid_t, std::shared_ptr<frontend::EventSink> const&, bool) override
2760+ pid_t, std::shared_ptr<frontend::EventSink> const&) override
2761 {
2762 return server;
2763 }
2764
2765=== modified file 'include/test/mir_test_doubles/stub_renderable.h'
2766--- include/test/mir_test_doubles/stub_renderable.h 2014-03-17 07:35:22 +0000
2767+++ include/test/mir_test_doubles/stub_renderable.h 2014-04-07 13:29:13 +0000
2768@@ -33,7 +33,7 @@
2769 class StubRenderable : public graphics::Renderable
2770 {
2771 public:
2772- std::shared_ptr<graphics::Buffer> buffer(unsigned long) const override
2773+ std::shared_ptr<graphics::Buffer> buffer(void const*) const override
2774 {
2775 return std::make_shared<StubBuffer>();
2776 }
2777@@ -53,7 +53,7 @@
2778 {
2779 return trans;
2780 }
2781- bool should_be_rendered_in(geometry::Rectangle const&) const override
2782+ bool visible() const
2783 {
2784 return true;
2785 }
2786
2787=== modified file 'include/test/mir_test_doubles/stub_session_authorizer.h'
2788--- include/test/mir_test_doubles/stub_session_authorizer.h 2013-08-28 03:41:48 +0000
2789+++ include/test/mir_test_doubles/stub_session_authorizer.h 2014-04-07 13:29:13 +0000
2790@@ -38,6 +38,10 @@
2791 {
2792 return true;
2793 }
2794+ bool screencast_is_allowed(pid_t)
2795+ {
2796+ return true;
2797+ }
2798 };
2799
2800 }
2801
2802=== removed file 'include/test/mir_test_doubles/stub_surface_builder.h'
2803--- include/test/mir_test_doubles/stub_surface_builder.h 2014-03-06 06:05:17 +0000
2804+++ include/test/mir_test_doubles/stub_surface_builder.h 1970-01-01 00:00:00 +0000
2805@@ -1,69 +0,0 @@
2806-/*
2807- * Copyright © 2013-2014 Canonical Ltd.
2808- *
2809- * This program is free software: you can redistribute it and/or modify it
2810- * under the terms of the GNU General Public License version 3,
2811- * as published by the Free Software Foundation.
2812- *
2813- * This program is distributed in the hope that it will be useful,
2814- * but WITHOUT ANY WARRANTY; without even the implied warranty of
2815- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
2816- * GNU General Public License for more details.
2817- *
2818- * You should have received a copy of the GNU General Public License
2819- * along with this program. If not, see <http://www.gnu.org/licenses/>.
2820- *
2821- * Authored by: Alan Griffiths <alan@octopull.co.uk>
2822- */
2823-
2824-
2825-#ifndef MIR_TEST_DOUBLES_STUB_SURFACE_BUILDER_H_
2826-#define MIR_TEST_DOUBLES_STUB_SURFACE_BUILDER_H_
2827-
2828-#include "src/server/scene/surface_builder.h"
2829-#include "src/server/scene/basic_surface.h"
2830-#include "src/server/report/null_report_factory.h"
2831-#include "mir/shell/surface_creation_parameters.h"
2832-
2833-#include "mir_test_doubles/stub_buffer_stream.h"
2834-#include <memory>
2835-namespace mir
2836-{
2837-namespace test
2838-{
2839-namespace doubles
2840-{
2841-
2842-class StubSurfaceBuilder : public scene::SurfaceBuilder
2843-{
2844-public:
2845- StubSurfaceBuilder() :
2846- dummy_surface(std::make_shared<scene::BasicSurface>(
2847- std::string("stub"),
2848- geometry::Rectangle{{},{}},
2849- [](){},
2850- false,
2851- std::make_shared<StubBufferStream>(),
2852- std::shared_ptr<input::InputChannel>(),
2853- mir::report::null_scene_report()))
2854- {
2855- }
2856-
2857- std::weak_ptr<scene::BasicSurface> create_surface(shell::SurfaceCreationParameters const&)
2858- {
2859- return dummy_surface;
2860- }
2861-
2862- void destroy_surface(std::weak_ptr<scene::BasicSurface> const& )
2863- {
2864- }
2865-
2866-private:
2867- std::shared_ptr<scene::BasicSurface> dummy_surface;
2868-};
2869-}
2870-}
2871-}
2872-
2873-
2874-#endif /* MIR_TEST_DOUBLES_STUB_SURFACE_BUILDER_H_ */
2875
2876=== removed file 'include/test/mir_test_doubles/stub_surface_ranker.h'
2877--- include/test/mir_test_doubles/stub_surface_ranker.h 2014-03-06 06:05:17 +0000
2878+++ include/test/mir_test_doubles/stub_surface_ranker.h 1970-01-01 00:00:00 +0000
2879@@ -1,44 +0,0 @@
2880-/*
2881- * Copyright © 2013 Canonical Ltd.
2882- *
2883- * This program is free software: you can redistribute it and/or modify it
2884- * under the terms of the GNU General Public License version 3,
2885- * as published by the Free Software Foundation.
2886- *
2887- * This program is distributed in the hope that it will be useful,
2888- * but WITHOUT ANY WARRANTY; without even the implied warranty of
2889- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
2890- * GNU General Public License for more details.
2891- *
2892- * You should have received a copy of the GNU General Public License
2893- * along with this program. If not, see <http://www.gnu.org/licenses/>.
2894- *
2895- * Authored by: Robert Carr <robert.carr@canonical.com>
2896- */
2897-
2898-
2899-#ifndef MIR_TEST_DOUBLES_STUB_SURFACE_RANKER_H_
2900-#define MIR_TEST_DOUBLES_STUB_SURFACE_RANKER_H_
2901-
2902-#include "src/server/scene/surface_ranker.h"
2903-
2904-namespace mir
2905-{
2906-namespace test
2907-{
2908-namespace doubles
2909-{
2910-
2911-struct StubSurfaceRanker : public scene::SurfaceRanker
2912-{
2913- void raise(std::weak_ptr<scene::BasicSurface> const&) override
2914- {
2915- }
2916-};
2917-
2918-}
2919-}
2920-}
2921-
2922-
2923-#endif /* MIR_TEST_DOUBLES_STUB_SURFACE_RANKER_H_ */
2924
2925=== added file 'include/test/mir_test_framework/declarative_placement_strategy.h'
2926--- include/test/mir_test_framework/declarative_placement_strategy.h 1970-01-01 00:00:00 +0000
2927+++ include/test/mir_test_framework/declarative_placement_strategy.h 2014-04-07 13:29:13 +0000
2928@@ -0,0 +1,64 @@
2929+/*
2930+ * Copyright © 2014 Canonical Ltd.
2931+ *
2932+ * This program is free software: you can redistribute it and/or modify it
2933+ * under the terms of the GNU General Public License version 3,
2934+ * as published by the Free Software Foundation.
2935+ *
2936+ * This program is distributed in the hope that it will be useful,
2937+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
2938+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
2939+ * GNU General Public License for more details.
2940+ *
2941+ * You should have received a copy of the GNU General Public License
2942+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
2943+ *
2944+ * Authored by: Robert Carr <robert.carr@canonical.com>
2945+ */
2946+
2947+#ifndef MIR_TEST_FRAMEWORK_DECLARATIVE_PLACEMENT_STRATEGY_H_
2948+#define MIR_TEST_FRAMEWORK_DECLARATIVE_PLACEMENT_STRATEGY_H_
2949+
2950+#include "mir/shell/placement_strategy.h"
2951+#include "mir/geometry/rectangle.h"
2952+#include "mir/scene/depth_id.h"
2953+
2954+#include <memory>
2955+#include <map>
2956+#include <string>
2957+
2958+namespace mir_test_framework
2959+{
2960+typedef std::map<std::string, mir::geometry::Rectangle> SurfaceGeometries;
2961+typedef std::map<std::string, mir::scene::DepthId> SurfaceDepths;
2962+
2963+/// DeclarativePlacementStrategy is a test utility server component for specifying
2964+/// a static list of surface geometries and relative depths. Used, for example,
2965+/// in input tests where it is necessary to set up scenarios depending on
2966+/// multiple surfaces geometry and stacking.
2967+class DeclarativePlacementStrategy : public mir::shell::PlacementStrategy
2968+{
2969+ public:
2970+ // Placement requests will be passed through to default strategy, and then overriden if the surface appears
2971+ // in the geometry or depth map. This allows for the convenience of leaving some surfaces geometries unspecified
2972+ // and receiving the default behavior.
2973+ DeclarativePlacementStrategy(std::shared_ptr<mir::shell::PlacementStrategy> const& default_strategy,
2974+ SurfaceGeometries const& positions_by_name, SurfaceDepths const& depths_by_name);
2975+
2976+ virtual ~DeclarativePlacementStrategy() = default;
2977+
2978+ mir::shell::SurfaceCreationParameters place(mir::shell::Session const& session, mir::shell::SurfaceCreationParameters const& request_parameters) override;
2979+
2980+protected:
2981+ DeclarativePlacementStrategy(const DeclarativePlacementStrategy&) = delete;
2982+ DeclarativePlacementStrategy& operator=(const DeclarativePlacementStrategy&) = delete;
2983+
2984+private:
2985+ std::shared_ptr<mir::shell::PlacementStrategy> const default_strategy;
2986+
2987+ SurfaceGeometries surface_geometries_by_name;
2988+ SurfaceDepths surface_depths_by_name;
2989+};
2990+}
2991+
2992+#endif // MIR_TEST_FRAMEWORK_DECLARATIVE_PLACEMENT_STRATEGY_H_
2993
2994=== modified file 'include/test/mir_test_framework/udev_environment.h'
2995--- include/test/mir_test_framework/udev_environment.h 2014-03-06 06:05:17 +0000
2996+++ include/test/mir_test_framework/udev_environment.h 2014-04-07 13:29:13 +0000
2997@@ -56,6 +56,7 @@
2998 void add_standard_device(std::string const& name);
2999
3000 UMockdevTestbed *testbed;
3001+ std::string const recordings_path;
3002 };
3003
3004 }
3005
3006=== modified file 'src/client/default_connection_configuration.cpp'
3007--- src/client/default_connection_configuration.cpp 2014-03-06 06:05:17 +0000
3008+++ src/client/default_connection_configuration.cpp 2014-04-07 13:29:13 +0000
3009@@ -103,7 +103,7 @@
3010 {
3011 auto const val_raw = getenv("MIR_CLIENT_PLATFORM_LIB");
3012 std::string const val{val_raw ? val_raw : default_platform_lib};
3013- auto const platform_lib = load_library(val);
3014+ auto const platform_lib = ::load_library(val);
3015
3016 auto const create_client_platform_factory =
3017 platform_lib->load_function<mcl::CreateClientPlatformFactory>(
3018
3019=== modified file 'src/client/lttng/input_receiver_report_tp.h'
3020--- src/client/lttng/input_receiver_report_tp.h 2014-02-03 11:44:32 +0000
3021+++ src/client/lttng/input_receiver_report_tp.h 2014-04-07 13:29:13 +0000
3022@@ -26,6 +26,7 @@
3023 #define MIR_CLIENT_LTTNG_INPUT_RECEIVER_REPORT_TP_H_
3024
3025 #include <lttng/tracepoint.h>
3026+#include <stdint.h>
3027
3028 #ifdef __clang__
3029 /*
3030
3031=== modified file 'src/client/lttng/rpc_report_tp.h'
3032--- src/client/lttng/rpc_report_tp.h 2014-03-06 06:05:17 +0000
3033+++ src/client/lttng/rpc_report_tp.h 2014-04-07 13:29:13 +0000
3034@@ -26,6 +26,7 @@
3035 #define MIR_CLIENT_LTTNG_RPC_REPORT_TP_H_
3036
3037 #include <lttng/tracepoint.h>
3038+#include <stdint.h>
3039
3040 #ifdef __clang__
3041 /*
3042
3043=== modified file 'src/client/mir_client_library.cpp'
3044--- src/client/mir_client_library.cpp 2014-03-06 06:05:17 +0000
3045+++ src/client/mir_client_library.cpp 2014-04-07 13:29:13 +0000
3046@@ -120,8 +120,17 @@
3047 {
3048 if (!error_connections.contains(connection))
3049 {
3050- auto wait_handle = connection->disconnect();
3051- wait_handle->wait_for_all();
3052+ try
3053+ {
3054+ auto wait_handle = connection->disconnect();
3055+ wait_handle->wait_for_all();
3056+ }
3057+ catch (std::exception const&)
3058+ {
3059+ // We're implementing a C API so no exceptions are to be
3060+ // propagated. And that's OK because if disconnect() fails,
3061+ // we don't care why. We're finished with the connection anyway.
3062+ }
3063 }
3064 else
3065 {
3066
3067=== modified file 'src/client/rpc/mir_basic_rpc_channel.cpp'
3068--- src/client/rpc/mir_basic_rpc_channel.cpp 2014-03-06 06:05:17 +0000
3069+++ src/client/rpc/mir_basic_rpc_channel.cpp 2014-04-07 13:29:13 +0000
3070@@ -34,7 +34,7 @@
3071 }
3072
3073 void mclrd::PendingCallCache::save_completion_details(
3074- mir::protobuf::wire::Invocation& invoke,
3075+ mir::protobuf::wire::Invocation const& invoke,
3076 google::protobuf::Message* response,
3077 std::shared_ptr<google::protobuf::Closure> const& complete)
3078 {
3079@@ -102,8 +102,8 @@
3080
3081
3082 mir::protobuf::wire::Invocation mclr::MirBasicRpcChannel::invocation_for(
3083- const google::protobuf::MethodDescriptor* method,
3084- const google::protobuf::Message* request)
3085+ google::protobuf::MethodDescriptor const* method,
3086+ google::protobuf::Message const* request)
3087 {
3088 char buffer[mir::frontend::serialization_buffer_size];
3089
3090
3091=== modified file 'src/client/rpc/mir_basic_rpc_channel.h'
3092--- src/client/rpc/mir_basic_rpc_channel.h 2014-03-06 06:05:17 +0000
3093+++ src/client/rpc/mir_basic_rpc_channel.h 2014-04-07 13:29:13 +0000
3094@@ -55,7 +55,7 @@
3095 PendingCallCache(std::shared_ptr<RpcReport> const& rpc_report);
3096
3097 void save_completion_details(
3098- mir::protobuf::wire::Invocation& invoke,
3099+ mir::protobuf::wire::Invocation const& invoke,
3100 google::protobuf::Message* response,
3101 std::shared_ptr<google::protobuf::Closure> const& complete);
3102
3103@@ -95,8 +95,9 @@
3104 ~MirBasicRpcChannel();
3105
3106 protected:
3107- mir::protobuf::wire::Invocation invocation_for(const google::protobuf::MethodDescriptor* method,
3108- const google::protobuf::Message* request);
3109+ mir::protobuf::wire::Invocation invocation_for(
3110+ google::protobuf::MethodDescriptor const* method,
3111+ google::protobuf::Message const* request);
3112 int next_id();
3113
3114 private:
3115
3116=== modified file 'src/client/rpc/mir_socket_rpc_channel.cpp'
3117--- src/client/rpc/mir_socket_rpc_channel.cpp 2014-03-06 06:05:17 +0000
3118+++ src/client/rpc/mir_socket_rpc_channel.cpp 2014-04-07 13:29:13 +0000
3119@@ -142,8 +142,39 @@
3120 {
3121 if (!disconnected.load())
3122 {
3123- auto surface = dynamic_cast<mir::protobuf::Surface*>(response);
3124- mir::protobuf::Screencast* screencast{nullptr};
3125+ auto const message_type = response->GetTypeName();
3126+
3127+ mir::protobuf::Surface* surface = nullptr;
3128+ mir::protobuf::Buffer* buffer = nullptr;
3129+ mir::protobuf::Platform* platform = nullptr;
3130+
3131+ if (message_type == "mir.protobuf.Buffer")
3132+ {
3133+ buffer = static_cast<mir::protobuf::Buffer*>(response);
3134+ }
3135+ else if (message_type == "mir.protobuf.Surface")
3136+ {
3137+ surface = static_cast<mir::protobuf::Surface*>(response);
3138+ if (surface && surface->has_buffer())
3139+ buffer = surface->mutable_buffer();
3140+ }
3141+ else if (message_type == "mir.protobuf.Screencast")
3142+ {
3143+ auto screencast = static_cast<mir::protobuf::Screencast*>(response);
3144+ if (screencast && screencast->has_buffer())
3145+ buffer = screencast->mutable_buffer();
3146+ }
3147+ else if (message_type == "mir.protobuf.Platform")
3148+ {
3149+ platform = static_cast<mir::protobuf::Platform*>(response);
3150+ }
3151+ else if (message_type == "mir.protobuf.Connection")
3152+ {
3153+ auto connection = static_cast<mir::protobuf::Connection*>(response);
3154+ if (connection && connection->has_platform())
3155+ platform = connection->mutable_platform();
3156+ }
3157+
3158 if (surface)
3159 {
3160 surface->clear_fd();
3161@@ -158,19 +189,6 @@
3162 rpc_report->file_descriptors_received(*response, fds);
3163 }
3164 }
3165- else
3166- {
3167- screencast = dynamic_cast<mir::protobuf::Screencast*>(response);
3168- }
3169-
3170- auto buffer = dynamic_cast<mir::protobuf::Buffer*>(response);
3171- if (!buffer)
3172- {
3173- if (surface && surface->has_buffer())
3174- buffer = surface->mutable_buffer();
3175- else if (screencast && screencast->has_buffer())
3176- buffer = screencast->mutable_buffer();
3177- }
3178
3179 if (buffer)
3180 {
3181@@ -187,14 +205,6 @@
3182 }
3183 }
3184
3185- auto platform = dynamic_cast<mir::protobuf::Platform*>(response);
3186- if (!platform)
3187- {
3188- auto connection = dynamic_cast<mir::protobuf::Connection*>(response);
3189- if (connection && connection->has_platform())
3190- platform = connection->mutable_platform();
3191- }
3192-
3193 if (platform)
3194 {
3195 platform->clear_fd();
3196@@ -266,7 +276,7 @@
3197 google::protobuf::Message* response,
3198 google::protobuf::Closure* complete)
3199 {
3200- mir::protobuf::wire::Invocation invocation = invocation_for(method, parameters);
3201+ auto const& invocation = invocation_for(method, parameters);
3202
3203 rpc_report->invocation_requested(invocation);
3204
3205@@ -345,7 +355,7 @@
3206 {
3207 const size_t body_size = read_message_header();
3208
3209- result = read_message_body(body_size);
3210+ read_message_body(result, body_size);
3211
3212 rpc_report->result_receipt_succeeded(result);
3213 }
3214@@ -431,18 +441,17 @@
3215 return body_size;
3216 }
3217
3218-mir::protobuf::wire::Result mclr::MirSocketRpcChannel::read_message_body(const size_t body_size)
3219+void mclr::MirSocketRpcChannel::read_message_body(
3220+ mir::protobuf::wire::Result& result,
3221+ size_t const body_size)
3222 {
3223 boost::system::error_code error;
3224- boost::asio::streambuf message;
3225- boost::asio::read(socket, message, boost::asio::transfer_exactly(body_size), error);
3226+ body_bytes.resize(body_size);
3227+ boost::asio::read(socket, boost::asio::buffer(body_bytes), error);
3228 if (error)
3229 {
3230 BOOST_THROW_EXCEPTION(std::runtime_error("Failed to read message body: " + error.message()));
3231 }
3232
3233- std::istream in(&message);
3234- mir::protobuf::wire::Result result;
3235- result.ParseFromIstream(&in);
3236- return result;
3237+ result.ParseFromArray(body_bytes.data(), body_size);
3238 }
3239
3240=== modified file 'src/client/rpc/mir_socket_rpc_channel.h'
3241--- src/client/rpc/mir_socket_rpc_channel.h 2014-03-06 06:05:17 +0000
3242+++ src/client/rpc/mir_socket_rpc_channel.h 2014-04-07 13:29:13 +0000
3243@@ -80,6 +80,7 @@
3244
3245 static size_t const size_of_header = 2;
3246 unsigned char header_bytes[size_of_header];
3247+ std::vector<char> body_bytes;
3248
3249 void receive_file_descriptors(google::protobuf::Message* response, google::protobuf::Closure* complete);
3250 void receive_file_descriptors(std::vector<int> &fds);
3251@@ -92,7 +93,8 @@
3252
3253 size_t read_message_header();
3254
3255- mir::protobuf::wire::Result read_message_body(const size_t body_size);
3256+ void read_message_body(mir::protobuf::wire::Result& result,
3257+ size_t const body_size);
3258 void notify_disconnected();
3259
3260 std::shared_ptr<SurfaceMap> surface_map;
3261
3262=== modified file 'src/platform/CMakeLists.txt'
3263--- src/platform/CMakeLists.txt 2014-03-06 06:05:17 +0000
3264+++ src/platform/CMakeLists.txt 2014-04-07 13:29:13 +0000
3265@@ -3,13 +3,14 @@
3266
3267 add_library(
3268 mirplatform SHARED
3269-
3270+ shared_library_loader.cpp
3271 udev_wrapper.cpp
3272 )
3273
3274 target_link_libraries(
3275 mirplatform
3276 mirplatformgraphicscommon
3277+ mirsharedsharedlibrary
3278
3279 ${UDEV_LDFLAGS} ${UDEV_LIBRARIES}
3280 )
3281
3282=== modified file 'src/platform/graphics/android/CMakeLists.txt'
3283--- src/platform/graphics/android/CMakeLists.txt 2014-03-11 13:44:57 +0000
3284+++ src/platform/graphics/android/CMakeLists.txt 2014-04-07 13:29:13 +0000
3285@@ -20,6 +20,7 @@
3286 hwc_layerlist.cpp
3287 hwc_layers.cpp
3288 hwc_fb_device.cpp
3289+ hwc_formatted_logger.cpp
3290 hwc_device.cpp
3291 hwc_common_device.cpp
3292 hwc_vsync.cpp
3293@@ -44,9 +45,12 @@
3294 target_link_libraries(
3295 mirplatformgraphicsandroid
3296
3297+ miroptions
3298 mirplatform
3299 mirsharedandroid
3300+ mirsharedenv
3301
3302+ ${Boost_PROGRAM_OPTIONS_LIBRARY}
3303 ${LIBHARDWARE_LIBRARIES}
3304 ${EGL_LDFLAGS} ${EGL_LIBRARIES}
3305 ${GLESv2_LDFLAGS} ${GLESv2_LIBRARIES}
3306
3307=== modified file 'src/platform/graphics/android/android_display.cpp'
3308--- src/platform/graphics/android/android_display.cpp 2014-03-17 07:35:22 +0000
3309+++ src/platform/graphics/android/android_display.cpp 2014-04-07 13:29:13 +0000
3310@@ -33,9 +33,10 @@
3311 namespace geom=mir::geometry;
3312
3313 mga::AndroidDisplay::AndroidDisplay(std::shared_ptr<mga::DisplayBuilder> const& display_builder,
3314+ std::shared_ptr<GLConfig> const& gl_config,
3315 std::shared_ptr<DisplayReport> const& display_report)
3316 : display_builder{display_builder},
3317- gl_context{display_builder->display_format(), *display_report},
3318+ gl_context{display_builder->display_format(), *gl_config, *display_report},
3319 display_buffer{display_builder->create_display_buffer(gl_context)}
3320 {
3321 display_report->report_successful_setup_of_native_resources();
3322
3323=== modified file 'src/platform/graphics/android/android_display.h'
3324--- src/platform/graphics/android/android_display.h 2014-03-06 06:05:17 +0000
3325+++ src/platform/graphics/android/android_display.h 2014-04-07 13:29:13 +0000
3326@@ -30,6 +30,7 @@
3327 {
3328
3329 class DisplayReport;
3330+class GLConfig;
3331
3332 namespace android
3333 {
3334@@ -41,6 +42,7 @@
3335 {
3336 public:
3337 explicit AndroidDisplay(std::shared_ptr<DisplayBuilder> const& display_builder,
3338+ std::shared_ptr<GLConfig> const& gl_config,
3339 std::shared_ptr<DisplayReport> const& display_report);
3340
3341 void for_each_display_buffer(std::function<void(graphics::DisplayBuffer&)> const& f);
3342
3343=== modified file 'src/platform/graphics/android/android_platform.cpp'
3344--- src/platform/graphics/android/android_platform.cpp 2014-03-06 06:05:17 +0000
3345+++ src/platform/graphics/android/android_platform.cpp 2014-04-07 13:29:13 +0000
3346@@ -31,6 +31,8 @@
3347 #include "mir/graphics/buffer_ipc_packer.h"
3348 #include "mir/graphics/display_report.h"
3349 #include "mir/options/option.h"
3350+#include "mir/options/configuration.h"
3351+#include "mir/abnormal_exit.h"
3352
3353 #include <boost/throw_exception.hpp>
3354 #include <stdexcept>
3355@@ -40,6 +42,26 @@
3356 namespace mf=mir::frontend;
3357 namespace mo = mir::options;
3358
3359+namespace
3360+{
3361+char const* const hwc_log_opt = "hwc-report";
3362+bool should_log_hwc(mo::Option const& options)
3363+{
3364+ if (!options.is_set(hwc_log_opt))
3365+ return false;
3366+
3367+ auto opt = options.get<std::string>(hwc_log_opt);
3368+ if (opt == mo::log_opt_value)
3369+ return true;
3370+ else if (opt == mo::off_opt_value)
3371+ return false;
3372+ else
3373+ throw mir::AbnormalExit(
3374+ std::string("Invalid hwc-report option: " + opt + " (valid options are: \"" +
3375+ mo::off_opt_value + "\" and \"" + mo::log_opt_value + "\")"));
3376+}
3377+}
3378+
3379 mga::AndroidPlatform::AndroidPlatform(
3380 std::shared_ptr<mga::DisplayBuilder> const& display_builder,
3381 std::shared_ptr<mg::DisplayReport> const& display_report)
3382@@ -61,9 +83,11 @@
3383 }
3384
3385 std::shared_ptr<mg::Display> mga::AndroidPlatform::create_display(
3386- std::shared_ptr<graphics::DisplayConfigurationPolicy> const&)
3387+ std::shared_ptr<graphics::DisplayConfigurationPolicy> const&,
3388+ std::shared_ptr<mg::GLConfig> const& gl_config)
3389 {
3390- return std::make_shared<mga::AndroidDisplay>(display_builder, display_report);
3391+ return std::make_shared<mga::AndroidDisplay>(
3392+ display_builder, gl_config, display_report);
3393 }
3394
3395 std::shared_ptr<mg::PlatformIPCPackage> mga::AndroidPlatform::get_ipc_package()
3396@@ -105,10 +129,10 @@
3397 return std::make_shared<mga::InternalClient>();
3398 }
3399
3400-extern "C" std::shared_ptr<mg::Platform> mg::create_platform(std::shared_ptr<mo::Option> const& /*options*/, std::shared_ptr<DisplayReport> const& display_report)
3401+extern "C" std::shared_ptr<mg::Platform> mg::create_platform(std::shared_ptr<mo::Option> const& options, std::shared_ptr<DisplayReport> const& display_report)
3402 {
3403 auto buffer_initializer = std::make_shared<mg::NullBufferInitializer>();
3404- auto display_resource_factory = std::make_shared<mga::ResourceFactory>();
3405+ auto display_resource_factory = std::make_shared<mga::ResourceFactory>(should_log_hwc(*options));
3406 auto fb_allocator = std::make_shared<mga::AndroidGraphicBufferAllocator>(buffer_initializer);
3407 auto display_builder = std::make_shared<mga::OutputBuilder>(
3408 fb_allocator, display_resource_factory, display_report);
3409@@ -121,3 +145,12 @@
3410 // mg::NativePlatform cannot create a display anyways, so it doesnt need a display builder
3411 return std::make_shared<mga::AndroidPlatform>(nullptr, display_report);
3412 }
3413+
3414+extern "C" void add_platform_options(
3415+ boost::program_options::options_description& config)
3416+{
3417+ config.add_options()
3418+ (hwc_log_opt,
3419+ boost::program_options::value<std::string>()->default_value(std::string{mo::off_opt_value}),
3420+ "[platform-specific] How to handle the HWC logging report. [{log,off}]");
3421+}
3422
3423=== modified file 'src/platform/graphics/android/android_platform.h'
3424--- src/platform/graphics/android/android_platform.h 2014-03-06 06:05:17 +0000
3425+++ src/platform/graphics/android/android_platform.h 2014-04-07 13:29:13 +0000
3426@@ -44,7 +44,8 @@
3427 std::shared_ptr<graphics::GraphicBufferAllocator> create_buffer_allocator(
3428 std::shared_ptr<BufferInitializer> const& buffer_initializer);
3429 std::shared_ptr<Display> create_display(
3430- std::shared_ptr<graphics::DisplayConfigurationPolicy> const&);
3431+ std::shared_ptr<graphics::DisplayConfigurationPolicy> const&,
3432+ std::shared_ptr<graphics::GLConfig> const& /*gl_config*/);
3433 std::shared_ptr<PlatformIPCPackage> get_ipc_package();
3434 std::shared_ptr<InternalClient> create_internal_client();
3435 void fill_ipc_package(BufferIPCPacker* packer, graphics::Buffer const* buffer) const;
3436
3437=== modified file 'src/platform/graphics/android/display_buffer.cpp'
3438--- src/platform/graphics/android/display_buffer.cpp 2014-03-11 13:44:57 +0000
3439+++ src/platform/graphics/android/display_buffer.cpp 2014-04-07 13:29:13 +0000
3440@@ -85,7 +85,7 @@
3441 }
3442
3443 void mga::DisplayBuffer::render_and_post_update(
3444- std::list<std::shared_ptr<Renderable>> const& renderlist,
3445+ RenderableList const& renderlist,
3446 std::function<void(Renderable const&)> const& render_fn)
3447 {
3448 if (renderlist.empty())
3449
3450=== modified file 'src/platform/graphics/android/display_buffer.h'
3451--- src/platform/graphics/android/display_buffer.h 2014-03-11 13:44:57 +0000
3452+++ src/platform/graphics/android/display_buffer.h 2014-04-07 13:29:13 +0000
3453@@ -50,7 +50,7 @@
3454 bool can_bypass() const override;
3455
3456 void render_and_post_update(
3457- std::list<std::shared_ptr<Renderable>> const& renderlist,
3458+ RenderableList const& renderlist,
3459 std::function<void(Renderable const&)> const& render_fn);
3460 MirOrientation orientation() const override;
3461
3462
3463=== modified file 'src/platform/graphics/android/display_device.h'
3464--- src/platform/graphics/android/display_device.h 2014-03-11 13:44:57 +0000
3465+++ src/platform/graphics/android/display_device.h 2014-04-07 13:29:13 +0000
3466@@ -44,7 +44,7 @@
3467 virtual void render_gl(SwappingGLContext const& context) = 0;
3468 virtual void render_gl_and_overlays(
3469 SwappingGLContext const& context,
3470- std::list<std::shared_ptr<Renderable>> const& list,
3471+ RenderableList const& list,
3472 std::function<void(Renderable const&)> const& render_fn) = 0;
3473 virtual void post(Buffer const& buffer) = 0;
3474 virtual bool apply_orientation(MirOrientation orientation) const = 0;
3475
3476=== modified file 'src/platform/graphics/android/fb_device.cpp'
3477--- src/platform/graphics/android/fb_device.cpp 2014-03-11 13:44:57 +0000
3478+++ src/platform/graphics/android/fb_device.cpp 2014-04-07 13:29:13 +0000
3479@@ -51,7 +51,7 @@
3480
3481 void mga::FBDevice::render_gl_and_overlays(
3482 SwappingGLContext const& context,
3483- std::list<std::shared_ptr<Renderable>> const& renderables,
3484+ RenderableList const& renderables,
3485 std::function<void(Renderable const&)> const& render_fn)
3486 {
3487 for(auto const& renderable : renderables)
3488
3489=== modified file 'src/platform/graphics/android/fb_device.h'
3490--- src/platform/graphics/android/fb_device.h 2014-03-11 13:44:57 +0000
3491+++ src/platform/graphics/android/fb_device.h 2014-04-07 13:29:13 +0000
3492@@ -40,7 +40,7 @@
3493 virtual void render_gl(SwappingGLContext const& context);
3494 virtual void render_gl_and_overlays(
3495 SwappingGLContext const& context,
3496- std::list<std::shared_ptr<Renderable>> const& list,
3497+ RenderableList const& list,
3498 std::function<void(Renderable const&)> const& render_fn);
3499 void post(Buffer const& buffer);
3500
3501
3502=== modified file 'src/platform/graphics/android/gl_context.cpp'
3503--- src/platform/graphics/android/gl_context.cpp 2014-03-12 02:46:58 +0000
3504+++ src/platform/graphics/android/gl_context.cpp 2014-04-07 13:29:13 +0000
3505@@ -19,6 +19,7 @@
3506 #include "gl_context.h"
3507 #include "android_format_conversion-inl.h"
3508 #include "mir/graphics/display_report.h"
3509+#include "mir/graphics/gl_config.h"
3510
3511 #include <algorithm>
3512 #include <boost/throw_exception.hpp>
3513@@ -31,13 +32,6 @@
3514 namespace
3515 {
3516
3517-static EGLint const required_egl_config_attr [] =
3518-{
3519- EGL_SURFACE_TYPE, EGL_WINDOW_BIT,
3520- EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT,
3521- EGL_NONE
3522-};
3523-
3524 static EGLint const default_egl_context_attr[] =
3525 {
3526 EGL_CONTEXT_CLIENT_VERSION, 2,
3527@@ -69,8 +63,19 @@
3528
3529 /* the minimum requirement is to have EGL_WINDOW_BIT and EGL_OPENGL_ES2_BIT, and to select a config
3530 whose pixel format matches that of the framebuffer. */
3531-static EGLConfig select_egl_config_with_format(EGLDisplay egl_display, MirPixelFormat display_format)
3532+EGLConfig select_egl_config_with_format(
3533+ EGLDisplay egl_display, MirPixelFormat display_format,
3534+ mg::GLConfig const& gl_config)
3535 {
3536+ EGLint const required_egl_config_attr [] =
3537+ {
3538+ EGL_SURFACE_TYPE, EGL_WINDOW_BIT,
3539+ EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT,
3540+ EGL_DEPTH_SIZE, gl_config.depth_buffer_bits(),
3541+ EGL_STENCIL_SIZE, gl_config.stencil_buffer_bits(),
3542+ EGL_NONE
3543+ };
3544+
3545 int required_visual_id = mga::to_android_format(display_format);
3546 int num_potential_configs;
3547 EGLint num_match_configs;
3548@@ -107,10 +112,12 @@
3549 return eglCreateWindowSurface(disp, config, native, NULL);
3550 }
3551
3552-mga::GLContext::GLContext(MirPixelFormat display_format, mg::DisplayReport& report)
3553+mga::GLContext::GLContext(MirPixelFormat display_format,
3554+ mg::GLConfig const& gl_config,
3555+ mg::DisplayReport& report)
3556 : egl_display(create_and_initialize_display()),
3557 own_display(true),
3558- egl_config(select_egl_config_with_format(egl_display, display_format)),
3559+ egl_config(select_egl_config_with_format(egl_display, display_format, gl_config)),
3560 egl_context{egl_display,
3561 eglCreateContext(egl_display, egl_config, EGL_NO_CONTEXT, default_egl_context_attr)},
3562 egl_surface{egl_display,
3563
3564=== modified file 'src/platform/graphics/android/gl_context.h'
3565--- src/platform/graphics/android/gl_context.h 2014-03-12 02:46:58 +0000
3566+++ src/platform/graphics/android/gl_context.h 2014-04-07 13:29:13 +0000
3567@@ -29,6 +29,7 @@
3568 namespace graphics
3569 {
3570 class DisplayReport;
3571+class GLConfig;
3572 namespace android
3573 {
3574
3575@@ -53,7 +54,9 @@
3576 {
3577 public:
3578 //For creating a gl context
3579- GLContext(MirPixelFormat display_format, DisplayReport& report);
3580+ GLContext(MirPixelFormat display_format,
3581+ GLConfig const& gl_config,
3582+ DisplayReport& report);
3583
3584 //For creating a gl context shared with another GLContext
3585 GLContext(GLContext const& shared_gl_context,
3586
3587=== modified file 'src/platform/graphics/android/hwc_common_device.cpp'
3588--- src/platform/graphics/android/hwc_common_device.cpp 2014-03-11 13:44:57 +0000
3589+++ src/platform/graphics/android/hwc_common_device.cpp 2014-04-07 13:29:13 +0000
3590@@ -44,8 +44,8 @@
3591
3592 mga::HWCCommonDevice::HWCCommonDevice(std::shared_ptr<hwc_composer_device_1> const& hwc_device,
3593 std::shared_ptr<mga::HWCVsyncCoordinator> const& coordinator)
3594- : hwc_device(hwc_device),
3595- coordinator(coordinator),
3596+ : coordinator(coordinator),
3597+ hwc_device(hwc_device),
3598 current_mode(mir_power_mode_on)
3599 {
3600 callbacks.hooks.invalidate = invalidate_hook;
3601
3602=== modified file 'src/platform/graphics/android/hwc_common_device.h'
3603--- src/platform/graphics/android/hwc_common_device.h 2014-03-06 06:05:17 +0000
3604+++ src/platform/graphics/android/hwc_common_device.h 2014-04-07 13:29:13 +0000
3605@@ -54,7 +54,6 @@
3606 HWCCommonDevice(std::shared_ptr<hwc_composer_device_1> const& hwc_device,
3607 std::shared_ptr<HWCVsyncCoordinator> const& coordinator);
3608
3609- std::shared_ptr<hwc_composer_device_1> const hwc_device;
3610 std::shared_ptr<HWCVsyncCoordinator> const coordinator;
3611 std::unique_lock<std::mutex> lock_unblanked();
3612
3613@@ -64,6 +63,8 @@
3614
3615 HWCCallbacks callbacks;
3616
3617+ std::shared_ptr<hwc_composer_device_1> const hwc_device;
3618+
3619 std::mutex blanked_mutex;
3620 std::condition_variable blanked_cond;
3621 MirPowerMode current_mode;
3622
3623=== modified file 'src/platform/graphics/android/hwc_device.cpp'
3624--- src/platform/graphics/android/hwc_device.cpp 2014-03-11 13:44:57 +0000
3625+++ src/platform/graphics/android/hwc_device.cpp 2014-04-07 13:29:13 +0000
3626@@ -21,6 +21,7 @@
3627 #include "hwc_device.h"
3628 #include "hwc_layerlist.h"
3629 #include "hwc_vsync_coordinator.h"
3630+#include "hwc_wrapper.h"
3631 #include "framebuffer_bundle.h"
3632 #include "buffer.h"
3633 #include "mir/graphics/buffer.h"
3634@@ -89,7 +90,7 @@
3635
3636 void mga::HwcDevice::render_gl_and_overlays(
3637 SwappingGLContext const& context,
3638- std::list<std::shared_ptr<Renderable>> const& renderables,
3639+ RenderableList const& renderables,
3640 std::function<void(Renderable const&)> const& render_fn)
3641 {
3642 if (!(list_needs_commit = hwc_list.update_list_and_check_if_changed(renderables, fbtarget_size)))
3643
3644=== modified file 'src/platform/graphics/android/hwc_device.h'
3645--- src/platform/graphics/android/hwc_device.h 2014-03-11 13:44:57 +0000
3646+++ src/platform/graphics/android/hwc_device.h 2014-04-07 13:29:13 +0000
3647@@ -35,20 +35,7 @@
3648 {
3649 class HWCVsyncCoordinator;
3650 class SyncFileOps;
3651-
3652-class HwcWrapper
3653-{
3654-public:
3655- virtual ~HwcWrapper() = default;
3656-
3657- virtual void prepare(hwc_display_contents_1_t&) const = 0;
3658- virtual void set(hwc_display_contents_1_t&) const = 0;
3659-
3660-protected:
3661- HwcWrapper() = default;
3662- HwcWrapper& operator=(HwcWrapper const&) = delete;
3663- HwcWrapper(HwcWrapper const&) = delete;
3664-};
3665+class HwcWrapper;
3666
3667 class HwcDevice : public HWCCommonDevice
3668 {
3669@@ -63,7 +50,7 @@
3670 virtual void render_gl(SwappingGLContext const& context);
3671 virtual void render_gl_and_overlays(
3672 SwappingGLContext const& context,
3673- std::list<std::shared_ptr<Renderable>> const& list,
3674+ RenderableList const& list,
3675 std::function<void(Renderable const&)> const& render_fn);
3676 void post(Buffer const& buffer);
3677
3678
3679=== modified file 'src/platform/graphics/android/hwc_fb_device.cpp'
3680--- src/platform/graphics/android/hwc_fb_device.cpp 2014-03-11 13:44:57 +0000
3681+++ src/platform/graphics/android/hwc_fb_device.cpp 2014-04-07 13:29:13 +0000
3682@@ -21,6 +21,7 @@
3683 #include "hwc_vsync_coordinator.h"
3684 #include "framebuffer_bundle.h"
3685 #include "android_format_conversion-inl.h"
3686+#include "hwc_wrapper.h"
3687 #include "mir/graphics/buffer.h"
3688 #include "mir/graphics/android/native_buffer.h"
3689
3690@@ -33,9 +34,11 @@
3691 namespace geom = mir::geometry;
3692
3693 mga::HwcFbDevice::HwcFbDevice(std::shared_ptr<hwc_composer_device_1> const& hwc_device,
3694+ std::shared_ptr<HwcWrapper> const& hwc_wrapper,
3695 std::shared_ptr<framebuffer_device_t> const& fb_device,
3696 std::shared_ptr<HWCVsyncCoordinator> const& coordinator)
3697 : HWCCommonDevice(hwc_device, coordinator),
3698+ hwc_wrapper(hwc_wrapper),
3699 fb_device(fb_device),
3700 layer_list{{},1}
3701 {
3702@@ -44,41 +47,33 @@
3703
3704 void mga::HwcFbDevice::gpu_render()
3705 {
3706- auto rc = 0;
3707- auto display_list = layer_list.native_list().lock();
3708- if (display_list)
3709+ if (auto display_list = layer_list.native_list().lock())
3710 {
3711 display_list->dpy = eglGetCurrentDisplay();
3712 display_list->sur = eglGetCurrentSurface(EGL_DRAW);
3713
3714 //set() may affect EGL state by calling eglSwapBuffers.
3715 //HWC 1.0 is the only version of HWC that can do this.
3716- hwc_display_contents_1_t* displays[num_displays] {display_list.get()};
3717- rc = hwc_device->set(hwc_device.get(), num_displays, displays);
3718+ hwc_wrapper->set(*display_list);
3719 }
3720-
3721- if ((rc != 0) || (!display_list))
3722+ else
3723 {
3724 std::stringstream ss;
3725- ss << "error during hwc set(). rc = " << std::hex << rc;
3726+ ss << "error locking list during hwc set()";
3727 BOOST_THROW_EXCEPTION(std::runtime_error(ss.str()));
3728 }
3729 }
3730
3731 void mga::HwcFbDevice::prepare()
3732 {
3733- auto rc = 0;
3734- auto display_list = layer_list.native_list().lock();
3735- if (display_list)
3736+ if (auto display_list = layer_list.native_list().lock())
3737 {
3738- hwc_display_contents_1_t* displays[num_displays] {display_list.get()};
3739- rc = hwc_device->prepare(hwc_device.get(), num_displays, displays);
3740+ hwc_wrapper->prepare(*display_list);
3741 }
3742-
3743- if ((rc != 0) || (!display_list))
3744+ else
3745 {
3746 std::stringstream ss;
3747- ss << "error during hwc prepare(). rc = " << std::hex << rc;
3748+ ss << "error accessing list during hwc prepare()";
3749 BOOST_THROW_EXCEPTION(std::runtime_error(ss.str()));
3750 }
3751 }
3752@@ -91,7 +86,7 @@
3753
3754 void mga::HwcFbDevice::render_gl_and_overlays(
3755 SwappingGLContext const&,
3756- std::list<std::shared_ptr<Renderable>> const& renderables,
3757+ RenderableList const& renderables,
3758 std::function<void(Renderable const&)> const& render_fn)
3759 {
3760 prepare();
3761
3762=== modified file 'src/platform/graphics/android/hwc_fb_device.h'
3763--- src/platform/graphics/android/hwc_fb_device.h 2014-03-11 13:44:57 +0000
3764+++ src/platform/graphics/android/hwc_fb_device.h 2014-04-07 13:29:13 +0000
3765@@ -30,24 +30,28 @@
3766 {
3767 namespace android
3768 {
3769+class HwcWrapper;
3770
3771 class HwcFbDevice : public HWCCommonDevice
3772 {
3773 public:
3774 HwcFbDevice(std::shared_ptr<hwc_composer_device_1> const& hwc_device,
3775+ std::shared_ptr<HwcWrapper> const& hwc_wrapper,
3776 std::shared_ptr<framebuffer_device_t> const& fb_device,
3777 std::shared_ptr<HWCVsyncCoordinator> const& coordinator);
3778
3779 virtual void render_gl(SwappingGLContext const& context);
3780 virtual void render_gl_and_overlays(
3781 SwappingGLContext const& context,
3782- std::list<std::shared_ptr<Renderable>> const& list,
3783+ RenderableList const& list,
3784 std::function<void(Renderable const&)> const& render_fn);
3785 void post(Buffer const& buffer);
3786
3787 private:
3788 void prepare();
3789 void gpu_render();
3790+
3791+ std::shared_ptr<HwcWrapper> const hwc_wrapper;
3792 std::shared_ptr<framebuffer_device_t> const fb_device;
3793 static int const num_displays{1};
3794 LayerList layer_list;
3795
3796=== added file 'src/platform/graphics/android/hwc_formatted_logger.cpp'
3797--- src/platform/graphics/android/hwc_formatted_logger.cpp 1970-01-01 00:00:00 +0000
3798+++ src/platform/graphics/android/hwc_formatted_logger.cpp 2014-04-07 13:29:13 +0000
3799@@ -0,0 +1,177 @@
3800+/*
3801+ * Copyright © 2014 Canonical Ltd.
3802+ *
3803+ * This program is free software: you can redistribute it and/or modify it
3804+ * under the terms of the GNU Lesser General Public License version 3,
3805+ * as published by the Free Software Foundation.
3806+ *
3807+ * This program is distributed in the hope that it will be useful,
3808+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
3809+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
3810+ * GNU Lesser General Public License for more details.
3811+ *
3812+ * You should have received a copy of the GNU Lesser General Public License
3813+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
3814+ *
3815+ * Authored by: Kevin DuBois <kevin.dubois@canonical.com>
3816+ */
3817+
3818+#include "hwc_formatted_logger.h"
3819+#include <iostream>
3820+#include <iomanip>
3821+
3822+namespace mga=mir::graphics::android;
3823+
3824+namespace
3825+{
3826+std::string const separator{" | "};
3827+int const layer_num_column_size{2};
3828+int const blending_column_size{8};
3829+int const rotation_column_size{9};
3830+int const rect_entry_column_size{4};
3831+int const type_column_size{9};
3832+
3833+class StreamFormatter
3834+{
3835+public:
3836+ StreamFormatter(std::ostream& str, unsigned int const width, std::ios_base::fmtflags flags)
3837+ : stream(str),
3838+ old_width(stream.width(width)),
3839+ old_flags(stream.setf(flags,std::ios::adjustfield))
3840+ {
3841+ }
3842+
3843+ ~StreamFormatter()
3844+ {
3845+ stream.setf(old_flags, std::ios::adjustfield);
3846+ stream.width(old_width);
3847+ }
3848+private:
3849+ std::ostream& stream;
3850+ unsigned int const old_width;
3851+ std::ios_base::fmtflags const old_flags;
3852+};
3853+
3854+struct LayerNumber{ unsigned int const num; };
3855+std::ostream& operator<<(std::ostream& str, LayerNumber l)
3856+{
3857+ StreamFormatter stream_format(str, layer_num_column_size, std::ios_base::right);
3858+ return str << l.num % 100;
3859+}
3860+
3861+struct HwcRotation{ unsigned int const key; };
3862+std::ostream& operator<<(std::ostream& str, HwcRotation rotation_key)
3863+{
3864+ StreamFormatter stream_format(str, rotation_column_size, std::ios_base::left);
3865+ switch(rotation_key.key)
3866+ {
3867+ case 0:
3868+ return str << std::string{"NONE"};
3869+ case HWC_TRANSFORM_ROT_90:
3870+ return str << std::string{"ROT_90"};
3871+ case HWC_TRANSFORM_ROT_180:
3872+ return str << std::string{"ROT_180"};
3873+ case HWC_TRANSFORM_ROT_270:
3874+ return str << std::string{"ROT_270"};
3875+ default:
3876+ return str << std::string{"UNKNOWN"};
3877+ }
3878+}
3879+
3880+struct HwcBlending{ int const key; };
3881+std::ostream& operator<<(std::ostream& str, HwcBlending blending_key)
3882+{
3883+ StreamFormatter stream_format(str, blending_column_size, std::ios_base::left);
3884+ switch(blending_key.key)
3885+ {
3886+ case HWC_BLENDING_NONE:
3887+ return str << std::string{"NONE"};
3888+ case HWC_BLENDING_PREMULT:
3889+ return str << std::string{"PREMULT"};
3890+ case HWC_BLENDING_COVERAGE:
3891+ return str << std::string{"COVERAGE"};
3892+ default:
3893+ return str << std::string{"UNKNOWN"};
3894+ }
3895+}
3896+
3897+struct HwcType{ int const type; unsigned int const flags; };
3898+std::ostream& operator<<(std::ostream& str, HwcType type)
3899+{
3900+ StreamFormatter stream_format(str, type_column_size, std::ios_base::left);
3901+ switch(type.type)
3902+ {
3903+ case HWC_OVERLAY:
3904+ return str << std::string{"OVERLAY"};
3905+ case HWC_FRAMEBUFFER:
3906+ if (type.flags == HWC_SKIP_LAYER)
3907+ return str << std::string{"FORCE_GL"};
3908+ else
3909+ return str << std::string{"GL_RENDER"};
3910+ case HWC_FRAMEBUFFER_TARGET:
3911+ return str << std::string{"FB_TARGET"};
3912+ default:
3913+ return str << std::string{"UNKNOWN"};
3914+ }
3915+}
3916+
3917+struct HwcRectMember { int member; };
3918+std::ostream& operator<<(std::ostream& str, HwcRectMember rect)
3919+{
3920+ StreamFormatter stream_format(str, rect_entry_column_size, std::ios_base::right);
3921+ return str << rect.member;
3922+}
3923+
3924+struct HwcRect { hwc_rect_t const& rect; };
3925+std::ostream& operator<<(std::ostream& str, HwcRect r)
3926+{
3927+ return str << "{"
3928+ << HwcRectMember{r.rect.left} << ","
3929+ << HwcRectMember{r.rect.top} << ","
3930+ << HwcRectMember{r.rect.right} << ","
3931+ << HwcRectMember{r.rect.bottom} << "}";
3932+}
3933+}
3934+
3935+void mga::HwcFormattedLogger::log_list_submitted_to_prepare(hwc_display_contents_1_t const& list) const
3936+{
3937+ std::cout << "before prepare():" << std::endl
3938+ << " # | pos {l,t,r,b} | crop {l,t,r,b} | transform | blending | "
3939+ << std::endl;
3940+ for(auto i = 0u; i < list.numHwLayers; i++)
3941+ std::cout << LayerNumber{i}
3942+ << separator
3943+ << HwcRect{list.hwLayers[i].displayFrame}
3944+ << separator
3945+ << HwcRect{list.hwLayers[i].sourceCrop}
3946+ << separator
3947+ << HwcRotation{list.hwLayers[i].transform}
3948+ << separator
3949+ << HwcBlending{list.hwLayers[i].blending}
3950+ << separator
3951+ << std::endl;
3952+}
3953+
3954+void mga::HwcFormattedLogger::log_prepare_done(hwc_display_contents_1_t const& list) const
3955+{
3956+ std::cout << "after prepare():" << std::endl
3957+ << " # | Type | " << std::endl;
3958+ for(auto i = 0u; i < list.numHwLayers; i++)
3959+ std::cout << LayerNumber{i}
3960+ << separator
3961+ << HwcType{list.hwLayers[i].compositionType,list.hwLayers[i].flags}
3962+ << separator
3963+ << std::endl;
3964+}
3965+
3966+void mga::HwcFormattedLogger::log_set_list(hwc_display_contents_1_t const& list) const
3967+{
3968+ std::cout << "set list():" << std::endl
3969+ << " # | handle" << std::endl;
3970+
3971+ for(auto i = 0u; i < list.numHwLayers; i++)
3972+ std::cout << LayerNumber{i}
3973+ << separator
3974+ << list.hwLayers[i].handle
3975+ << std::endl;
3976+}
3977
3978=== added file 'src/platform/graphics/android/hwc_formatted_logger.h'
3979--- src/platform/graphics/android/hwc_formatted_logger.h 1970-01-01 00:00:00 +0000
3980+++ src/platform/graphics/android/hwc_formatted_logger.h 2014-04-07 13:29:13 +0000
3981@@ -0,0 +1,41 @@
3982+/*
3983+ * Copyright © 2014 Canonical Ltd.
3984+ *
3985+ * This program is free software: you can redistribute it and/or modify it
3986+ * under the terms of the GNU Lesser General Public License version 3,
3987+ * as published by the Free Software Foundation.
3988+ *
3989+ * This program is distributed in the hope that it will be useful,
3990+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
3991+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
3992+ * GNU Lesser General Public License for more details.
3993+ *
3994+ * You should have received a copy of the GNU Lesser General Public License
3995+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
3996+ *
3997+ * Authored by: Kevin DuBois <kevin.dubois@canonical.com>
3998+ */
3999+
4000+#ifndef MIR_GRAPHICS_ANDROID_HWC_FORMATTED_LOGGER_H_
4001+#define MIR_GRAPHICS_ANDROID_HWC_FORMATTED_LOGGER_H_
4002+
4003+#include "hwc_logger.h"
4004+
4005+namespace mir
4006+{
4007+namespace graphics
4008+{
4009+namespace android
4010+{
4011+class HwcFormattedLogger : public HwcLogger
4012+{
4013+public:
4014+ HwcFormattedLogger() = default;
4015+ void log_list_submitted_to_prepare(hwc_display_contents_1_t const& list) const override;
4016+ void log_prepare_done(hwc_display_contents_1_t const& list) const override;
4017+ void log_set_list(hwc_display_contents_1_t const& list) const override;
4018+};
4019+}
4020+}
4021+}
4022+#endif /* MIR_GRAPHICS_ANDROID_HWC_FORMATTED_LOGGER_H_ */
4023
4024=== modified file 'src/platform/graphics/android/hwc_layerlist.cpp'
4025--- src/platform/graphics/android/hwc_layerlist.cpp 2014-03-17 07:35:22 +0000
4026+++ src/platform/graphics/android/hwc_layerlist.cpp 2014-04-07 13:29:13 +0000
4027@@ -52,7 +52,7 @@
4028 }
4029
4030 bool mga::LayerList::update_list_and_check_if_changed(
4031- std::list<std::shared_ptr<mg::Renderable>> const& renderlist,
4032+ RenderableList const& renderlist,
4033 size_t additional_layers)
4034 {
4035 size_t needed_size = renderlist.size() + additional_layers;
4036@@ -70,7 +70,7 @@
4037 {
4038 layers_it->set_render_parameters(
4039 renderable->screen_position(), renderable->alpha_enabled());
4040- layers_it->set_buffer(*renderable->buffer(1));// TODO: remove needing to know about frameno
4041+ layers_it->set_buffer(*renderable->buffer(this));
4042 any_buffer_updated |= layers_it->needs_hwc_commit();
4043 layers_it++;
4044 }
4045@@ -88,7 +88,7 @@
4046 renderable->screen_position(),
4047 renderable->alpha_enabled(),
4048 hwc_representation, i++));
4049- new_layers.back().set_buffer(*renderable->buffer(1));// TODO: remove needing to know about frameno
4050+ new_layers.back().set_buffer(*renderable->buffer(this));
4051 }
4052
4053 for(; i < needed_size; i++)
4054@@ -137,7 +137,7 @@
4055 }
4056
4057 mga::LayerList::LayerList(
4058- std::list<std::shared_ptr<mg::Renderable>> const& renderlist,
4059+ RenderableList const& renderlist,
4060 size_t additional_layers)
4061 {
4062 update_list_and_check_if_changed(renderlist, additional_layers);
4063
4064=== modified file 'src/platform/graphics/android/hwc_layerlist.h'
4065--- src/platform/graphics/android/hwc_layerlist.h 2014-03-11 13:44:57 +0000
4066+++ src/platform/graphics/android/hwc_layerlist.h 2014-04-07 13:29:13 +0000
4067@@ -48,9 +48,9 @@
4068 class LayerList
4069 {
4070 public:
4071- LayerList(std::list<std::shared_ptr<Renderable>> const& renderlist, size_t additional_layers);
4072+ LayerList(RenderableList const& renderlist, size_t additional_layers);
4073 bool update_list_and_check_if_changed(
4074- std::list<std::shared_ptr<Renderable>> const& renderlist,
4075+ RenderableList const& renderlist,
4076 size_t additional_layers);
4077
4078 std::list<HWCLayer>::iterator begin();
4079
4080=== added file 'src/platform/graphics/android/hwc_logger.h'
4081--- src/platform/graphics/android/hwc_logger.h 1970-01-01 00:00:00 +0000
4082+++ src/platform/graphics/android/hwc_logger.h 2014-04-07 13:29:13 +0000
4083@@ -0,0 +1,46 @@
4084+/*
4085+ * Copyright © 2014 Canonical Ltd.
4086+ *
4087+ * This program is free software: you can redistribute it and/or modify it
4088+ * under the terms of the GNU Lesser General Public License version 3,
4089+ * as published by the Free Software Foundation.
4090+ *
4091+ * This program is distributed in the hope that it will be useful,
4092+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
4093+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
4094+ * GNU Lesser General Public License for more details.
4095+ *
4096+ * You should have received a copy of the GNU Lesser General Public License
4097+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
4098+ *
4099+ * Authored by: Kevin DuBois <kevin.dubois@canonical.com>
4100+ */
4101+
4102+#ifndef MIR_GRAPHICS_ANDROID_HWC_LOGGER_H_
4103+#define MIR_GRAPHICS_ANDROID_HWC_LOGGER_H_
4104+
4105+#include <hardware/hwcomposer.h>
4106+
4107+namespace mir
4108+{
4109+namespace graphics
4110+{
4111+namespace android
4112+{
4113+class HwcLogger
4114+{
4115+public:
4116+ virtual ~HwcLogger() = default;
4117+
4118+ virtual void log_list_submitted_to_prepare(hwc_display_contents_1_t const& list) const = 0;
4119+ virtual void log_prepare_done(hwc_display_contents_1_t const& list) const = 0;
4120+ virtual void log_set_list(hwc_display_contents_1_t const& list) const = 0;
4121+protected:
4122+ HwcLogger() = default;
4123+ HwcLogger& operator=(HwcLogger const&) = delete;
4124+ HwcLogger(HwcLogger const&) = delete;
4125+};
4126+}
4127+}
4128+}
4129+#endif /* MIR_GRAPHICS_ANDROID_HWC_LOGGER_H_ */
4130
4131=== added file 'src/platform/graphics/android/hwc_wrapper.h'
4132--- src/platform/graphics/android/hwc_wrapper.h 1970-01-01 00:00:00 +0000
4133+++ src/platform/graphics/android/hwc_wrapper.h 2014-04-07 13:29:13 +0000
4134@@ -0,0 +1,47 @@
4135+/*
4136+ * Copyright © 2014 Canonical Ltd.
4137+ *
4138+ * This program is free software: you can redistribute it and/or modify it
4139+ * under the terms of the GNU Lesser General Public License version 3,
4140+ * as published by the Free Software Foundation.
4141+ *
4142+ * This program is distributed in the hope that it will be useful,
4143+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
4144+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
4145+ * GNU Lesser General Public License for more details.
4146+ *
4147+ * You should have received a copy of the GNU Lesser General Public License
4148+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
4149+ *
4150+ * Authored by: Kevin DuBois <kevin.dubois@canonical.com>
4151+ */
4152+
4153+#ifndef MIR_GRAPHICS_ANDROID_HWC_WRAPPER_H_
4154+#define MIR_GRAPHICS_ANDROID_HWC_WRAPPER_H_
4155+
4156+#include <hardware/hwcomposer.h>
4157+
4158+namespace mir
4159+{
4160+namespace graphics
4161+{
4162+namespace android
4163+{
4164+class HwcWrapper
4165+{
4166+public:
4167+ virtual ~HwcWrapper() = default;
4168+
4169+ virtual void prepare(hwc_display_contents_1_t&) const = 0;
4170+ virtual void set(hwc_display_contents_1_t&) const = 0;
4171+
4172+protected:
4173+ HwcWrapper() = default;
4174+ HwcWrapper& operator=(HwcWrapper const&) = delete;
4175+ HwcWrapper(HwcWrapper const&) = delete;
4176+};
4177+}
4178+}
4179+}
4180+
4181+#endif /* MIR_GRAPHICS_ANDROID_HWC_WRAPPER_H_ */
4182
4183=== modified file 'src/platform/graphics/android/real_hwc_wrapper.cpp'
4184--- src/platform/graphics/android/real_hwc_wrapper.cpp 2014-02-26 22:22:15 +0000
4185+++ src/platform/graphics/android/real_hwc_wrapper.cpp 2014-04-07 13:29:13 +0000
4186@@ -17,14 +17,18 @@
4187 */
4188
4189 #include "real_hwc_wrapper.h"
4190+#include "hwc_logger.h"
4191 #include <boost/throw_exception.hpp>
4192 #include <stdexcept>
4193 #include <sstream>
4194
4195 namespace mga=mir::graphics::android;
4196
4197-mga::RealHwcWrapper::RealHwcWrapper(std::shared_ptr<hwc_composer_device_1> const& hwc_device)
4198- : hwc_device(hwc_device)
4199+mga::RealHwcWrapper::RealHwcWrapper(
4200+ std::shared_ptr<hwc_composer_device_1> const& hwc_device,
4201+ std::shared_ptr<mga::HwcLogger> const& logger)
4202+ : hwc_device(hwc_device),
4203+ logger(logger)
4204 {
4205 }
4206
4207@@ -33,17 +37,22 @@
4208 //note, although we only have a primary display right now,
4209 // set the external and virtual displays to null as some drivers check for that
4210 hwc_display_contents_1_t* displays[num_displays] {&display_list, nullptr, nullptr};
4211+
4212+ logger->log_list_submitted_to_prepare(display_list);
4213 if (auto rc = hwc_device->prepare(hwc_device.get(), 1, displays))
4214 {
4215 std::stringstream ss;
4216 ss << "error during hwc prepare(). rc = " << std::hex << rc;
4217 BOOST_THROW_EXCEPTION(std::runtime_error(ss.str()));
4218 }
4219+ logger->log_prepare_done(display_list);
4220 }
4221
4222 void mga::RealHwcWrapper::set(hwc_display_contents_1_t& display_list) const
4223 {
4224 hwc_display_contents_1_t* displays[num_displays] {&display_list, nullptr, nullptr};
4225+
4226+ logger->log_set_list(display_list);
4227 if (auto rc = hwc_device->set(hwc_device.get(), 1, displays))
4228 {
4229 std::stringstream ss;
4230
4231=== modified file 'src/platform/graphics/android/real_hwc_wrapper.h'
4232--- src/platform/graphics/android/real_hwc_wrapper.h 2014-02-20 22:20:34 +0000
4233+++ src/platform/graphics/android/real_hwc_wrapper.h 2014-04-07 13:29:13 +0000
4234@@ -19,7 +19,7 @@
4235 #ifndef MIR_GRAPHICS_ANDROID_REAL_HWC_WRAPPER_H_
4236 #define MIR_GRAPHICS_ANDROID_REAL_HWC_WRAPPER_H_
4237
4238-#include "hwc_device.h"
4239+#include "hwc_wrapper.h"
4240 #include <memory>
4241 #include <hardware/hwcomposer.h>
4242
4243@@ -29,17 +29,20 @@
4244 {
4245 namespace android
4246 {
4247-
4248+class HwcLogger;
4249 class RealHwcWrapper : public HwcWrapper
4250 {
4251 public:
4252- RealHwcWrapper(std::shared_ptr<hwc_composer_device_1> const& hwc_device);
4253+ RealHwcWrapper(
4254+ std::shared_ptr<hwc_composer_device_1> const& hwc_device,
4255+ std::shared_ptr<HwcLogger> const& logger);
4256
4257 void prepare(hwc_display_contents_1_t&) const override;
4258 void set(hwc_display_contents_1_t&) const override;
4259 private:
4260 static size_t const num_displays{3}; //primary, external, virtual
4261 std::shared_ptr<hwc_composer_device_1> const hwc_device;
4262+ std::shared_ptr<HwcLogger> const logger;
4263 };
4264
4265 }
4266
4267=== modified file 'src/platform/graphics/android/resource_factory.cpp'
4268--- src/platform/graphics/android/resource_factory.cpp 2014-03-11 13:44:57 +0000
4269+++ src/platform/graphics/android/resource_factory.cpp 2014-04-07 13:29:13 +0000
4270@@ -31,6 +31,7 @@
4271 #include "hwc_vsync.h"
4272 #include "android_display.h"
4273 #include "real_hwc_wrapper.h"
4274+#include "hwc_formatted_logger.h"
4275
4276 #include <boost/throw_exception.hpp>
4277 #include <stdexcept>
4278@@ -39,6 +40,11 @@
4279 namespace mg = mir::graphics;
4280 namespace mga=mir::graphics::android;
4281
4282+mga::ResourceFactory::ResourceFactory(bool should_log_hwc)
4283+ : should_log_hwc{should_log_hwc}
4284+{
4285+}
4286+
4287 std::shared_ptr<framebuffer_device_t> mga::ResourceFactory::create_fb_native_device() const
4288 {
4289 hw_module_t const* module;
4290@@ -89,12 +95,37 @@
4291 return std::make_shared<mga::FBDevice>(fb_native_device);
4292 }
4293
4294+namespace
4295+{
4296+struct NullHwcLogger : public mga::HwcLogger
4297+{
4298+ void log_list_submitted_to_prepare(hwc_display_contents_1_t const&) const override
4299+ {
4300+ }
4301+ void log_prepare_done(hwc_display_contents_1_t const&) const override
4302+ {
4303+ }
4304+ void log_set_list(hwc_display_contents_1_t const&) const override
4305+ {
4306+ }
4307+};
4308+
4309+std::shared_ptr<mga::HwcLogger> make_logger(bool should_log)
4310+{
4311+ if (should_log)
4312+ return std::make_shared<mga::HwcFormattedLogger>();
4313+ else
4314+ return std::make_shared<NullHwcLogger>();
4315+}
4316+
4317+}
4318+
4319 std::shared_ptr<mga::DisplayDevice> mga::ResourceFactory::create_hwc_device(
4320 std::shared_ptr<hwc_composer_device_1> const& hwc_native_device) const
4321 {
4322 auto syncer = std::make_shared<mga::HWCVsync>();
4323 auto file_ops = std::make_shared<mga::RealSyncFileOps>();
4324- auto wrapper = std::make_shared<mga::RealHwcWrapper>(hwc_native_device);
4325+ auto wrapper = std::make_shared<mga::RealHwcWrapper>(hwc_native_device, make_logger(should_log_hwc));
4326 return std::make_shared<mga::HwcDevice>(hwc_native_device, wrapper, syncer, file_ops);
4327 }
4328
4329@@ -103,5 +134,7 @@
4330 std::shared_ptr<framebuffer_device_t> const& fb_native_device) const
4331 {
4332 auto syncer = std::make_shared<mga::HWCVsync>();
4333- return std::make_shared<mga::HwcFbDevice>(hwc_native_device, fb_native_device, syncer);
4334+ auto logger = std::make_shared<NullHwcLogger>();
4335+ auto wrapper = std::make_shared<mga::RealHwcWrapper>(hwc_native_device, make_logger(should_log_hwc));
4336+ return std::make_shared<mga::HwcFbDevice>(hwc_native_device, wrapper, fb_native_device, syncer);
4337 }
4338
4339=== modified file 'src/platform/graphics/android/resource_factory.h'
4340--- src/platform/graphics/android/resource_factory.h 2014-03-06 06:05:17 +0000
4341+++ src/platform/graphics/android/resource_factory.h 2014-04-07 13:29:13 +0000
4342@@ -31,6 +31,8 @@
4343 class ResourceFactory : public DisplayResourceFactory
4344 {
4345 public:
4346+ ResourceFactory(bool should_log_hwc);
4347+
4348 //native allocations
4349 std::shared_ptr<hwc_composer_device_1> create_hwc_native_device() const;
4350 std::shared_ptr<framebuffer_device_t> create_fb_native_device() const;
4351@@ -46,6 +48,8 @@
4352
4353 std::shared_ptr<ANativeWindow> create_native_window(
4354 std::shared_ptr<FramebufferBundle> const& fb_bundle) const;
4355+private:
4356+ bool const should_log_hwc;
4357 };
4358
4359 }
4360
4361=== modified file 'src/platform/graphics/mesa/CMakeLists.txt'
4362--- src/platform/graphics/mesa/CMakeLists.txt 2014-03-10 03:02:32 +0000
4363+++ src/platform/graphics/mesa/CMakeLists.txt 2014-04-07 13:29:13 +0000
4364@@ -47,6 +47,7 @@
4365 mirplatformgraphicsmesa
4366 mirplatform
4367
4368+ ${Boost_PROGRAM_OPTIONS_LIBRARY}
4369 ${DRM_LDFLAGS} ${DRM_LIBRARIES}
4370 ${GBM_LDFLAGS} ${GBM_LIBRARIES}
4371 ${EGL_LDFLAGS} ${EGL_LIBRARIES}
4372
4373=== modified file 'src/platform/graphics/mesa/display.cpp'
4374--- src/platform/graphics/mesa/display.cpp 2014-03-17 07:35:22 +0000
4375+++ src/platform/graphics/mesa/display.cpp 2014-04-07 13:29:13 +0000
4376@@ -54,7 +54,10 @@
4377 class GBMGLContext : public mg::GLContext
4378 {
4379 public:
4380- GBMGLContext(mgm::helpers::GBMHelper const& gbm, EGLContext shared_context)
4381+ GBMGLContext(mgm::helpers::GBMHelper const& gbm,
4382+ mg::GLConfig const& gl_config,
4383+ EGLContext shared_context)
4384+ : egl{gl_config}
4385 {
4386 egl.setup(gbm, shared_context);
4387 }
4388@@ -77,13 +80,16 @@
4389
4390 mgm::Display::Display(std::shared_ptr<Platform> const& platform,
4391 std::shared_ptr<DisplayConfigurationPolicy> const& initial_conf_policy,
4392+ std::shared_ptr<GLConfig> const& gl_config,
4393 std::shared_ptr<DisplayReport> const& listener)
4394 : platform(platform),
4395 listener(listener),
4396 monitor(mir::udev::Context()),
4397+ shared_egl{*gl_config},
4398 output_container{platform->drm.fd,
4399 std::make_shared<KMSPageFlipper>(platform->drm.fd)},
4400- current_display_configuration{platform->drm.fd}
4401+ current_display_configuration{platform->drm.fd},
4402+ gl_config{gl_config}
4403 {
4404 platform->vt->set_graphics_mode();
4405
4406@@ -203,6 +209,7 @@
4407 std::move(surface),
4408 bounding_rect,
4409 orientation,
4410+ *gl_config,
4411 shared_egl.context()}};
4412
4413 display_buffers_new.push_back(std::move(db));
4414@@ -320,7 +327,10 @@
4415 std::unique_ptr<mg::GLContext> mgm::Display::create_gl_context()
4416 {
4417 return std::unique_ptr<GBMGLContext>{
4418- new GBMGLContext{platform->gbm, shared_egl.context()}};
4419+ new GBMGLContext{
4420+ platform->gbm,
4421+ *gl_config,
4422+ shared_egl.context()}};
4423 }
4424
4425 void mgm::Display::clear_connected_unused_outputs()
4426
4427=== modified file 'src/platform/graphics/mesa/display.h'
4428--- src/platform/graphics/mesa/display.h 2014-03-06 06:05:17 +0000
4429+++ src/platform/graphics/mesa/display.h 2014-04-07 13:29:13 +0000
4430@@ -41,6 +41,7 @@
4431 class DisplayBuffer;
4432 class DisplayConfigurationPolicy;
4433 class EventHandlerRegister;
4434+class GLConfig;
4435
4436 namespace mesa
4437 {
4438@@ -54,8 +55,9 @@
4439 {
4440 public:
4441 Display(std::shared_ptr<Platform> const& platform,
4442- std::shared_ptr<DisplayConfigurationPolicy> const& initial_conf_policy,
4443- std::shared_ptr<DisplayReport> const& listener);
4444+ std::shared_ptr<DisplayConfigurationPolicy> const& initial_conf_policy,
4445+ std::shared_ptr<GLConfig> const& gl_config,
4446+ std::shared_ptr<DisplayReport> const& listener);
4447 ~Display();
4448
4449 geometry::Rectangle view_area() const;
4450@@ -92,6 +94,7 @@
4451 RealKMSOutputContainer output_container;
4452 mutable RealKMSDisplayConfiguration current_display_configuration;
4453 std::shared_ptr<Cursor> cursor;
4454+ std::shared_ptr<GLConfig> const gl_config;
4455 };
4456
4457 }
4458
4459=== modified file 'src/platform/graphics/mesa/display_buffer.cpp'
4460--- src/platform/graphics/mesa/display_buffer.cpp 2014-03-06 06:05:17 +0000
4461+++ src/platform/graphics/mesa/display_buffer.cpp 2014-04-07 13:29:13 +0000
4462@@ -101,6 +101,7 @@
4463 GBMSurfaceUPtr surface_gbm_param,
4464 geom::Rectangle const& area,
4465 MirOrientation rot,
4466+ GLConfig const& gl_config,
4467 EGLContext shared_context)
4468 : last_flipped_bufobj{nullptr},
4469 scheduled_bufobj{nullptr},
4470@@ -109,6 +110,7 @@
4471 drm(platform->drm),
4472 outputs(outputs),
4473 surface_gbm{std::move(surface_gbm_param)},
4474+ egl{gl_config},
4475 area(area),
4476 rotation(rot),
4477 needs_set_crtc{false},
4478@@ -196,7 +198,7 @@
4479 }
4480
4481 void mgm::DisplayBuffer::render_and_post_update(
4482- std::list<std::shared_ptr<Renderable>> const&,
4483+ RenderableList const&,
4484 std::function<void(Renderable const&)> const&)
4485 {
4486 post_update(nullptr);
4487
4488=== modified file 'src/platform/graphics/mesa/display_buffer.h'
4489--- src/platform/graphics/mesa/display_buffer.h 2014-03-06 06:05:17 +0000
4490+++ src/platform/graphics/mesa/display_buffer.h 2014-04-07 13:29:13 +0000
4491@@ -32,6 +32,7 @@
4492 {
4493
4494 class DisplayReport;
4495+class GLConfig;
4496
4497 namespace mesa
4498 {
4499@@ -49,6 +50,7 @@
4500 GBMSurfaceUPtr surface_gbm,
4501 geometry::Rectangle const& area,
4502 MirOrientation rot,
4503+ GLConfig const& gl_config,
4504 EGLContext shared_context);
4505 ~DisplayBuffer();
4506
4507@@ -59,7 +61,7 @@
4508
4509 bool can_bypass() const override;
4510 void post_update(std::shared_ptr<graphics::Buffer> bypass_buf) override;
4511- void render_and_post_update(std::list<std::shared_ptr<Renderable>> const& renderlist,
4512+ void render_and_post_update(RenderableList const& renderlist,
4513 std::function<void(Renderable const&)> const& render_fn);
4514 MirOrientation orientation() const override;
4515 void schedule_set_crtc();
4516
4517=== modified file 'src/platform/graphics/mesa/display_helpers.cpp'
4518--- src/platform/graphics/mesa/display_helpers.cpp 2014-03-12 02:46:58 +0000
4519+++ src/platform/graphics/mesa/display_helpers.cpp 2014-04-07 13:29:13 +0000
4520@@ -19,6 +19,7 @@
4521 #include "display_helpers.h"
4522 #include "drm_close_threadsafe.h"
4523
4524+#include "mir/graphics/gl_config.h"
4525 #include "mir/udev/wrapper.h"
4526
4527 #include <boost/exception/errinfo_errno.hpp>
4528@@ -219,7 +220,7 @@
4529 sv.drm_dd_major = -1; /* Don't care */
4530 sv.drm_dd_minor = -1; /* Don't care */
4531
4532- if ((error = drmSetInterfaceVersion(tmp_fd, &sv)))
4533+ if ((error = -drmSetInterfaceVersion(tmp_fd, &sv)))
4534 {
4535 close(tmp_fd);
4536 tmp_fd = -1;
4537@@ -238,7 +239,7 @@
4538 {
4539 BOOST_THROW_EXCEPTION(
4540 boost::enable_error_info(
4541- std::runtime_error("Error opening DRM device")) << boost::errinfo_errno(-error));
4542+ std::runtime_error("Error opening DRM device")) << boost::errinfo_errno(error));
4543 }
4544
4545 return tmp_fd;
4546@@ -295,6 +296,15 @@
4547 * EGLHelper *
4548 *************/
4549
4550+mgmh::EGLHelper::EGLHelper(GLConfig const& gl_config)
4551+ : depth_buffer_bits{gl_config.depth_buffer_bits()},
4552+ stencil_buffer_bits{gl_config.stencil_buffer_bits()},
4553+ egl_display{EGL_NO_DISPLAY}, egl_config{0},
4554+ egl_context{EGL_NO_CONTEXT}, egl_surface{EGL_NO_SURFACE},
4555+ should_terminate_egl{false}
4556+{
4557+}
4558+
4559 void mgmh::EGLHelper::setup(GBMHelper const& gbm)
4560 {
4561 static const EGLint context_attr[] = {
4562@@ -378,12 +388,14 @@
4563
4564 void mgmh::EGLHelper::setup_internal(GBMHelper const& gbm, bool initialize)
4565 {
4566- static const EGLint config_attr[] = {
4567+ EGLint const config_attr[] = {
4568 EGL_SURFACE_TYPE, EGL_WINDOW_BIT,
4569 EGL_RED_SIZE, 8,
4570 EGL_GREEN_SIZE, 8,
4571 EGL_BLUE_SIZE, 8,
4572 EGL_ALPHA_SIZE, 0,
4573+ EGL_DEPTH_SIZE, depth_buffer_bits,
4574+ EGL_STENCIL_SIZE, stencil_buffer_bits,
4575 EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT,
4576 EGL_NONE
4577 };
4578
4579=== modified file 'src/platform/graphics/mesa/display_helpers.h'
4580--- src/platform/graphics/mesa/display_helpers.h 2014-03-12 02:46:58 +0000
4581+++ src/platform/graphics/mesa/display_helpers.h 2014-04-07 13:29:13 +0000
4582@@ -37,6 +37,8 @@
4583 {
4584 namespace graphics
4585 {
4586+class GLConfig;
4587+
4588 namespace mesa
4589 {
4590
4591@@ -92,11 +94,7 @@
4592 class EGLHelper
4593 {
4594 public:
4595- EGLHelper()
4596- : egl_display{EGL_NO_DISPLAY}, egl_config{0},
4597- egl_context{EGL_NO_CONTEXT}, egl_surface{EGL_NO_SURFACE},
4598- should_terminate_egl{false} {}
4599-
4600+ EGLHelper(GLConfig const& gl_config);
4601 ~EGLHelper() noexcept;
4602
4603 EGLHelper(const EGLHelper&) = delete;
4604@@ -117,6 +115,8 @@
4605 private:
4606 void setup_internal(GBMHelper const& gbm, bool initialize);
4607
4608+ EGLint const depth_buffer_bits;
4609+ EGLint const stencil_buffer_bits;
4610 EGLDisplay egl_display;
4611 EGLConfig egl_config;
4612 EGLContext egl_context;
4613
4614=== modified file 'src/platform/graphics/mesa/platform.cpp'
4615--- src/platform/graphics/mesa/platform.cpp 2014-03-13 07:47:55 +0000
4616+++ src/platform/graphics/mesa/platform.cpp 2014-04-07 13:29:13 +0000
4617@@ -147,11 +147,13 @@
4618 }
4619
4620 std::shared_ptr<mg::Display> mgm::Platform::create_display(
4621- std::shared_ptr<DisplayConfigurationPolicy> const& initial_conf_policy)
4622+ std::shared_ptr<DisplayConfigurationPolicy> const& initial_conf_policy,
4623+ std::shared_ptr<GLConfig> const& gl_config)
4624 {
4625 return std::make_shared<mgm::Display>(
4626 this->shared_from_this(),
4627 initial_conf_policy,
4628+ gl_config,
4629 listener);
4630 }
4631
4632@@ -219,3 +221,11 @@
4633 return (display == mgm::NativePlatform::internal_native_display().get());
4634 return 0;
4635 }
4636+
4637+extern "C" void add_platform_options(boost::program_options::options_description& config)
4638+{
4639+ config.add_options()
4640+ ("vt",
4641+ boost::program_options::value<int>()->default_value(0),
4642+ "[platform-specific] VT to run on or 0 to use current.");
4643+}
4644
4645=== modified file 'src/platform/graphics/mesa/platform.h'
4646--- src/platform/graphics/mesa/platform.h 2014-03-06 06:05:17 +0000
4647+++ src/platform/graphics/mesa/platform.h 2014-04-07 13:29:13 +0000
4648@@ -47,7 +47,8 @@
4649 std::shared_ptr<graphics::GraphicBufferAllocator> create_buffer_allocator(
4650 const std::shared_ptr<BufferInitializer>& buffer_initializer);
4651 std::shared_ptr<graphics::Display> create_display(
4652- std::shared_ptr<DisplayConfigurationPolicy> const& initial_conf_policy);
4653+ std::shared_ptr<DisplayConfigurationPolicy> const& initial_conf_policy,
4654+ std::shared_ptr<GLConfig> const& gl_config);
4655 std::shared_ptr<PlatformIPCPackage> get_ipc_package();
4656 std::shared_ptr<InternalClient> create_internal_client();
4657
4658
4659=== modified file 'src/platform/options/default_configuration.cpp'
4660--- src/platform/options/default_configuration.cpp 2014-03-17 07:35:22 +0000
4661+++ src/platform/options/default_configuration.cpp 2014-04-07 13:29:13 +0000
4662@@ -16,7 +16,10 @@
4663 * Authored by: Alan Griffiths <alan@octopull.co.uk>
4664 */
4665
4666+#include "mir/shared_library.h"
4667+#include "mir/shared_library_loader.h"
4668 #include "mir/options/default_configuration.h"
4669+#include "mir/graphics/platform.h"
4670 #include "mir/default_configuration.h"
4671 #include "mir/abnormal_exit.h"
4672
4673@@ -114,9 +117,35 @@
4674 (name_opt, po::value<std::string>(),
4675 "When nested, the name Mir uses when registering with the host.")
4676 (offscreen_opt,
4677- "Render to offscreen buffers instead of the real outputs.")
4678- ("vt", po::value<int>()->default_value(0), // TODO this not applicable on all graphics platforms
4679- "VT to run on or 0 to use current.");
4680+ "Render to offscreen buffers instead of the real outputs.");
4681+
4682+ add_platform_options();
4683+}
4684+
4685+void mo::DefaultConfiguration::add_platform_options()
4686+{
4687+ namespace po = boost::program_options;
4688+ po::options_description program_options;
4689+ program_options.add_options()
4690+ (platform_graphics_lib,
4691+ po::value<std::string>()->default_value(default_platform_graphics_lib), "");
4692+ mo::ProgramOption options;
4693+ options.parse_arguments(program_options, argc, argv);
4694+
4695+ std::string graphics_libname;
4696+ auto env_libname = ::getenv("MIR_SERVER_PLATFORM_GRAPHICS_LIB");
4697+ if (!options.is_set(platform_graphics_lib) && env_libname)
4698+ {
4699+ graphics_libname = std::string{env_libname};
4700+ }
4701+ else
4702+ {
4703+ graphics_libname = options.get<std::string>(platform_graphics_lib);
4704+ }
4705+
4706+ auto graphics_lib = load_library(graphics_libname);
4707+ auto add_platform_options = graphics_lib->load_function<mir::graphics::AddPlatformOptions>(std::string("add_platform_options"));
4708+ add_platform_options(*this->program_options);
4709 }
4710
4711 boost::program_options::options_description_easy_init mo::DefaultConfiguration::add_options()
4712
4713=== added file 'src/platform/shared_library_loader.cpp'
4714--- src/platform/shared_library_loader.cpp 1970-01-01 00:00:00 +0000
4715+++ src/platform/shared_library_loader.cpp 2014-04-07 13:29:13 +0000
4716@@ -0,0 +1,38 @@
4717+/*
4718+ * Copyright © 2013 Canonical Ltd.
4719+ *
4720+ * This program is free software: you can redistribute it and/or modify it
4721+ * under the terms of the GNU Lesser General Public License version 3,
4722+ * as published by the Free Software Foundation.
4723+ *
4724+ * This program is distributed in the hope that it will be useful,
4725+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
4726+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
4727+ * GNU Lesser General Public License for more details.
4728+ *
4729+ * You should have received a copy of the GNU Lesser General Public License
4730+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
4731+ *
4732+ * Authored by: Kevin DuBois <kevin.dubois@canonical.com>
4733+ */
4734+
4735+#include "mir/shared_library_loader.h"
4736+#include "mir/shared_library.h"
4737+#include <memory>
4738+#include <map>
4739+
4740+mir::SharedLibrary const* mir::load_library(std::string const& libname)
4741+{
4742+ // There's no point in loading twice, and it isn't safe to unload...
4743+ static std::map<std::string, std::shared_ptr<mir::SharedLibrary>> libraries_cache;
4744+
4745+ if (auto& ptr = libraries_cache[libname])
4746+ {
4747+ return ptr.get();
4748+ }
4749+ else
4750+ {
4751+ ptr = std::make_shared<mir::SharedLibrary>(libname);
4752+ return ptr.get();
4753+ }
4754+}
4755
4756=== modified file 'src/server/CMakeLists.txt'
4757--- src/server/CMakeLists.txt 2014-03-12 06:41:13 +0000
4758+++ src/server/CMakeLists.txt 2014-04-07 13:29:13 +0000
4759@@ -94,7 +94,7 @@
4760 )
4761 endif()
4762
4763-set(MIRSERVER_ABI 17)
4764+set(MIRSERVER_ABI 18)
4765
4766 set_target_properties(
4767 mirserver
4768
4769=== modified file 'src/server/compositor/buffer_bundle.h'
4770--- src/server/compositor/buffer_bundle.h 2014-03-07 03:15:55 +0000
4771+++ src/server/compositor/buffer_bundle.h 2014-04-07 13:29:13 +0000
4772@@ -36,8 +36,20 @@
4773 virtual ~BufferBundle() noexcept {}
4774 virtual void client_acquire(std::function<void(graphics::Buffer* buffer)> complete) = 0;
4775 virtual void client_release(graphics::Buffer*) = 0;
4776+
4777+ /**
4778+ * Acquire the next buffer that's ready to display/composite.
4779+ *
4780+ * \param [in] user_id A unique identifier of who is going to use the
4781+ * buffer, to ensure that separate users representing
4782+ * separate monitors who need the same frame will get
4783+ * the same buffer. However consecutive calls for the
4784+ * same user will get different buffers. To avoid
4785+ * collisions, all callers should determine user_id
4786+ * in the same way (e.g. always use "this" pointer).
4787+ */
4788 virtual std::shared_ptr<graphics::Buffer>
4789- compositor_acquire(unsigned long frameno) = 0;
4790+ compositor_acquire(void const* user_id) = 0;
4791 virtual void compositor_release(std::shared_ptr<graphics::Buffer> const&) = 0;
4792 virtual std::shared_ptr<graphics::Buffer> snapshot_acquire() = 0;
4793 virtual void snapshot_release(std::shared_ptr<graphics::Buffer> const&) = 0;
4794
4795=== modified file 'src/server/compositor/buffer_stream_surfaces.cpp'
4796--- src/server/compositor/buffer_stream_surfaces.cpp 2014-03-07 03:15:55 +0000
4797+++ src/server/compositor/buffer_stream_surfaces.cpp 2014-04-07 13:29:13 +0000
4798@@ -38,10 +38,10 @@
4799 }
4800
4801 std::shared_ptr<mg::Buffer> mc::BufferStreamSurfaces::lock_compositor_buffer(
4802- unsigned long frameno)
4803+ void const* user_id)
4804 {
4805 return std::make_shared<mc::TemporaryCompositorBuffer>(
4806- buffer_bundle, frameno);
4807+ buffer_bundle, user_id);
4808 }
4809
4810 std::shared_ptr<mg::Buffer> mc::BufferStreamSurfaces::lock_snapshot_buffer()
4811
4812=== modified file 'src/server/compositor/buffer_stream_surfaces.h'
4813--- src/server/compositor/buffer_stream_surfaces.h 2014-03-07 03:15:55 +0000
4814+++ src/server/compositor/buffer_stream_surfaces.h 2014-04-07 13:29:13 +0000
4815@@ -42,7 +42,7 @@
4816 void swap_client_buffers(graphics::Buffer* old_buffer, std::function<void(graphics::Buffer* new_buffer)> complete) override;
4817
4818 std::shared_ptr<graphics::Buffer>
4819- lock_compositor_buffer(unsigned long frameno) override;
4820+ lock_compositor_buffer(void const* user_id) override;
4821 std::shared_ptr<graphics::Buffer> lock_snapshot_buffer() override;
4822
4823 MirPixelFormat get_stream_pixel_format() override;
4824
4825=== modified file 'src/server/compositor/bypass.cpp'
4826--- src/server/compositor/bypass.cpp 2014-03-17 07:35:22 +0000
4827+++ src/server/compositor/bypass.cpp 2014-04-07 13:29:13 +0000
4828@@ -44,9 +44,14 @@
4829
4830 auto const& view_area = display_buffer.view_area();
4831
4832+ //TODO: remove this check, why are we getting a non visible renderable
4833+ // in the list of surfaces?
4834+ if (!renderable.visible())
4835+ return false;
4836+
4837 // Not weirdly transformed but also not on this monitor? Don't care...
4838 // This will also check the surface is not hidden and has been posted.
4839- if (!renderable.should_be_rendered_in(view_area))
4840+ if (!view_area.contains(renderable.screen_position()))
4841 return false;
4842
4843 topmost_fits = false;
4844
4845=== modified file 'src/server/compositor/default_display_buffer_compositor.cpp'
4846--- src/server/compositor/default_display_buffer_compositor.cpp 2014-03-17 07:35:22 +0000
4847+++ src/server/compositor/default_display_buffer_compositor.cpp 2014-04-07 13:29:13 +0000
4848@@ -29,41 +29,35 @@
4849 #include "occlusion.h"
4850 #include <mutex>
4851 #include <cstdlib>
4852-#include <vector>
4853+#include <algorithm>
4854
4855 namespace mc = mir::compositor;
4856 namespace mg = mir::graphics;
4857
4858+//TODO remove VisibilityFilter once we don't need filters/operators for rendering
4859 namespace
4860 {
4861-
4862-struct FilterForVisibleSceneInRegion : public mc::FilterForScene
4863+struct VisibilityFilter : public mc::FilterForScene
4864 {
4865- FilterForVisibleSceneInRegion(
4866- mir::geometry::Rectangle const& enclosing_region,
4867- mc::OcclusionMatch const& occlusions)
4868- : enclosing_region(enclosing_region),
4869- occlusions(occlusions)
4870+public:
4871+ VisibilityFilter(
4872+ mg::RenderableList const& renderable_list)
4873+ : list(renderable_list)
4874 {
4875 }
4876+
4877 bool operator()(mg::Renderable const& r)
4878 {
4879- return r.should_be_rendered_in(enclosing_region) &&
4880- !occlusions.occluded(r);
4881+ auto matcher = [&r](std::shared_ptr<mg::Renderable> const& renderable)
4882+ {
4883+ return (renderable.get() == &r);
4884+ };
4885+ return (std::find_if(list.begin(), list.end(), matcher) != list.end());
4886 }
4887
4888- mir::geometry::Rectangle const& enclosing_region;
4889- mc::OcclusionMatch const& occlusions;
4890+private:
4891+ mg::RenderableList const& list;
4892 };
4893-
4894-std::mutex global_frameno_lock;
4895-unsigned long global_frameno = 0;
4896-
4897-bool wrapped_greater_or_equal(unsigned long a, unsigned long b)
4898-{
4899- return (a - b) < (~0UL / 2UL);
4900-}
4901-
4902 }
4903
4904 mc::DefaultDisplayBufferCompositor::DefaultDisplayBufferCompositor(
4905@@ -75,29 +69,14 @@
4906 scene{scene},
4907 renderer{renderer},
4908 report{report},
4909- local_frameno{global_frameno}
4910+ last_pass_rendered_anything{false}
4911 {
4912 }
4913
4914-
4915 bool mc::DefaultDisplayBufferCompositor::composite()
4916 {
4917 report->began_frame(this);
4918
4919- /*
4920- * Increment frame counts for each tick of the fastest instance of
4921- * DefaultDisplayBufferCompositor. This means for the fastest refresh
4922- * rate of all attached outputs.
4923- */
4924- local_frameno++;
4925- {
4926- std::lock_guard<std::mutex> lock(global_frameno_lock);
4927- if (wrapped_greater_or_equal(local_frameno, global_frameno))
4928- global_frameno = local_frameno;
4929- else
4930- local_frameno = global_frameno;
4931- }
4932-
4933 static bool const bypass_env{[]
4934 {
4935 auto const env = getenv("MIR_BYPASS");
4936@@ -123,8 +102,13 @@
4937
4938 if (filter.fullscreen_on_top())
4939 {
4940- auto bypass_buf =
4941- match.topmost_fullscreen()->buffer(local_frameno);
4942+ /*
4943+ * Notice the user_id we pass to buffer() here has to be
4944+ * different to the one used in the Renderer. This is in case
4945+ * the below if() fails we want to complete the frame using the
4946+ * same buffer (different user_id required).
4947+ */
4948+ auto bypass_buf = match.topmost_fullscreen()->buffer(this);
4949
4950 if (bypass_buf->can_bypass())
4951 {
4952@@ -140,41 +124,32 @@
4953
4954 if (!bypassed)
4955 {
4956- // preserves buffers used in rendering until after post_update()
4957- std::vector<std::shared_ptr<void>> saved_resources;
4958- auto save_resource = [&](std::shared_ptr<void> const& r)
4959- {
4960- saved_resources.push_back(r);
4961- };
4962-
4963 display_buffer.make_current();
4964
4965 auto const& view_area = display_buffer.view_area();
4966+ auto renderable_list = scene->generate_renderable_list();
4967+ mc::filter_occlusions_from(renderable_list, view_area);
4968
4969- mc::OcclusionFilter occlusion_search(view_area);
4970- mc::OcclusionMatch occlusion_match;
4971- scene->reverse_for_each_if(occlusion_search, occlusion_match);
4972+ for(auto const& renderable : renderable_list)
4973+ uncomposited_buffers |= (renderable->buffers_ready_for_compositor() > 1);
4974
4975 renderer->set_rotation(display_buffer.orientation());
4976 renderer->begin();
4977- mc::RenderingOperator applicator(*renderer, save_resource, local_frameno, uncomposited_buffers);
4978- FilterForVisibleSceneInRegion selector(view_area, occlusion_match);
4979+ mc::RenderingOperator applicator(*renderer);
4980+ VisibilityFilter selector(renderable_list);
4981 scene->for_each_if(selector, applicator);
4982 renderer->end();
4983
4984 display_buffer.post_update();
4985
4986 // This is a frig to avoid lp:1286190
4987- if (size_of_last_pass)
4988- {
4989- uncomposited_buffers |= saved_resources.empty();
4990- }
4991+ if (last_pass_rendered_anything && renderable_list.empty())
4992+ uncomposited_buffers = true;
4993
4994- size_of_last_pass = saved_resources.size();
4995+ last_pass_rendered_anything = !renderable_list.empty();
4996 // End of frig
4997 }
4998
4999 report->finished_frame(bypassed, this);
5000 return uncomposited_buffers;
The diff has been truncated for viewing.

Subscribers

People subscribed via source and target branches