@@ -213,7 +213,7 @@ const char* drm_fourcc_to_string(uint32_t fourcc) {
213213 return result ;
214214}
215215
216- int modeset_find_plane (int fd , struct modeset_output * out , struct drm_object * plane_out , uint32_t plane_format )
216+ int modeset_find_plane (int fd , struct modeset_output * out , struct drm_object * plane_out , uint32_t plane_format , uint32_t plane_id_override )
217217{
218218 drmModePlaneResPtr plane_res ;
219219 bool found_plane = false;
@@ -226,6 +226,33 @@ int modeset_find_plane(int fd, struct modeset_output *out, struct drm_object *pl
226226 return - ENOENT ;
227227 }
228228
229+ if (plane_id_override ) {
230+ // Try to use the user-specified plane id
231+ drmModePlanePtr plane = drmModeGetPlane (fd , plane_id_override );
232+ if (!plane ) {
233+ fprintf (stderr , "drmModeGetPlane(%u) failed: %s\n" , plane_id_override , strerror (errno ));
234+ drmModeFreePlaneResources (plane_res );
235+ return - ENOENT ;
236+ }
237+ if (plane -> possible_crtcs & (1 << out -> crtc_index )) {
238+ for (int j = 0 ; j < plane -> count_formats ; j ++ ) {
239+ if (plane -> formats [j ] == plane_format ) {
240+ found_plane = true;
241+ plane_out -> id = plane_id_override ;
242+ ret = 0 ;
243+ break ;
244+ }
245+ }
246+ }
247+ if (!found_plane ) {
248+ fprintf (stderr , "Specified plane id %u does not support required format or CRTC\n" , plane_id_override );
249+ ret = - EINVAL ;
250+ }
251+ drmModeFreePlane (plane );
252+ drmModeFreePlaneResources (plane_res );
253+ return ret ;
254+ }
255+
229256 for (i = 0 ; (i < plane_res -> count_planes ) && !found_plane ; i ++ ) {
230257 int plane_id = plane_res -> planes [i ];
231258
@@ -414,7 +441,7 @@ void modeset_output_destroy(int fd, struct modeset_output *out)
414441 free (out );
415442}
416443
417- struct modeset_output * modeset_output_create (int fd , drmModeRes * res , drmModeConnector * conn , uint16_t mode_width , uint16_t mode_height , uint32_t mode_vrefresh )
444+ struct modeset_output * modeset_output_create (int fd , drmModeRes * res , drmModeConnector * conn , uint16_t mode_width , uint16_t mode_height , uint32_t mode_vrefresh , uint32_t video_plane_id , uint32_t osd_plane_id )
418445{
419446 int ret ;
420447 struct modeset_output * out ;
@@ -475,14 +502,14 @@ struct modeset_output *modeset_output_create(int fd, drmModeRes *res, drmModeCon
475502 goto out_blob ;
476503 }
477504
478- ret = modeset_find_plane (fd , out , & out -> video_plane , DRM_FORMAT_NV12 );
505+ ret = modeset_find_plane (fd , out , & out -> video_plane , DRM_FORMAT_NV12 , video_plane_id );
479506 if (ret ) {
480507 fprintf (stderr , "no valid video plane with format NV12 for crtc %u\n" , out -> crtc .id );
481508 goto out_blob ;
482509 }
483510 fprintf (stdout , "Using plane %d (NV12) for Video\n" , out -> video_plane .id );
484511
485- ret = modeset_find_plane (fd , out , & out -> osd_plane , DRM_FORMAT_ARGB8888 );
512+ ret = modeset_find_plane (fd , out , & out -> osd_plane , DRM_FORMAT_ARGB8888 , osd_plane_id );
486513 if (ret ) {
487514 fprintf (stderr , "no valid osd plane with format ARGB8888 for crtc %u\n" , out -> crtc .id );
488515 goto out_blob ;
@@ -560,7 +587,7 @@ void *modeset_print_modes(int fd)
560587
561588}
562589
563- struct modeset_output * modeset_prepare (int fd , uint16_t mode_width , uint16_t mode_height , uint32_t mode_vrefresh )
590+ struct modeset_output * modeset_prepare (int fd , uint16_t mode_width , uint16_t mode_height , uint32_t mode_vrefresh , uint32_t video_plane_id , uint32_t osd_plane_id )
564591{
565592 drmModeRes * res ;
566593 drmModeConnector * conn ;
@@ -582,7 +609,7 @@ struct modeset_output *modeset_prepare(int fd, uint16_t mode_width, uint16_t mod
582609 continue ;
583610 }
584611
585- out = modeset_output_create (fd , res , conn , mode_width , mode_height , mode_vrefresh );
612+ out = modeset_output_create (fd , res , conn , mode_width , mode_height , mode_vrefresh , video_plane_id , osd_plane_id );
586613 drmModeFreeConnector (conn );
587614 if (out ) {
588615 drmModeFreeResources (res );
0 commit comments