summaryrefslogtreecommitdiff
path: root/xine/BluRay/input_bluray.c
diff options
context:
space:
mode:
Diffstat (limited to 'xine/BluRay/input_bluray.c')
-rw-r--r--xine/BluRay/input_bluray.c169
1 files changed, 43 insertions, 126 deletions
diff --git a/xine/BluRay/input_bluray.c b/xine/BluRay/input_bluray.c
index 1e3a20d4..92a3c4f3 100644
--- a/xine/BluRay/input_bluray.c
+++ b/xine/BluRay/input_bluray.c
@@ -42,8 +42,8 @@
#include <errno.h>
#include <dlfcn.h>
-#include <bluray.h>
-#include <libbdnav/navigation.h>
+#include <libbluray/bluray.h>
+#include <libbluray/navigation.h>
#define LOG_MODULE "input_bluray"
#define LOG_VERBOSE
@@ -98,72 +98,20 @@ typedef struct {
char *disc_root;
BLURAY *bdh;
- NAV_TITLE *nav_title;
} bluray_input_plugin_t;
-static int open_clip (bluray_input_plugin_t *this, NAV_CLIP *clip)
-{
- /* NOTE: bluray.h bd_select_title() actually opens CLIP, not TITLE ! */
-
- int clip_id;
- if (sscanf(clip->name, "%d.m2ts", &clip_id) != 1)
- clip_id = 0;
-
- lprintf("Selecting clip %d: bd_select_title(%d - %s) for title %s\n",
- clip_id, clip_id, clip->name, this->nav_title->name);
-
- if (!bd_select_title(this->bdh, clip_id)) {
- LOGMSG("bd_select_title(%d) failed: %s\n", clip_id, strerror(errno));
- _x_message(this->stream, XINE_MSG_FILE_NOT_FOUND, this->mrl, NULL);
-
- return -1;
- }
-
- lprintf("Clip length: %"PRIu64" bytes\n", (uint64_t)this->bdh->s_size);
-
- return 1;
-}
-
-static int next_clip (bluray_input_plugin_t *this)
-{
- /* select clip */
-
- NAV_CLIP *clip = nav_next_clip(this->nav_title, NULL);
- if (!clip) {
- LOGMSG("nav_next_clip() FAILED\n");
- return -1;
- }
- lprintf("clip change: title %s clip %s (%d clips, %d chapters)\n",
- this->nav_title->name, clip->name,
- this->nav_title->clip_list.count, this->nav_title->chap_list.count);
-
- /* open clip */
-
- return open_clip(this, clip);
-}
-
static int open_title (bluray_input_plugin_t *this, int title)
{
- if (this->nav_title)
- nav_title_close(this->nav_title);
-
- /* open title */
-
- char mpls[11] = {0};
- snprintf(mpls, sizeof(mpls), "%05d.mpls", MIN(99999, MAX(0, title)));
-
- this->nav_title = nav_title_open(this->disc_root, mpls);
-
- if (!this->nav_title) {
- LOGMSG("nav_title_open(%s, %s) FAILED\n", this->disc_root, mpls);
- return -1;
+ if (bd_select_playlist(this->bdh, title) <= 0 || !this->bdh->title) {
+ LOGMSG("bd_select_playlist(%d) failed\n", title);
+ return 0;
}
#ifdef LOG
- int ms = this->nav_title->duration / TICKS_IN_MS;
- lprintf("Opened title %s. Length %"PRId64" bytes / %02d:%02d:%02d.%03d\n",
- this->nav_title->name, (int64_t)this->nav_title->packets * PKT_SIZE,
+ int ms = this->bdh->title->duration / TICKS_IN_MS;
+ lprintf("Opened playlist %s. Length %"PRId64" bytes / %02d:%02d:%02d.%03d\n",
+ this->bdh->title->name, (int64_t)this->bdh->title->packets * PKT_SIZE,
ms / 3600000, (ms % 3600000 / 60000), (ms % 60000) / 1000, ms % 1000);
#endif
@@ -182,12 +130,12 @@ static int open_title (bluray_input_plugin_t *this, int title)
}
_x_stream_info_set(this->stream, XINE_STREAM_INFO_DVD_TITLE_NUMBER, title);
- _x_stream_info_set(this->stream, XINE_STREAM_INFO_DVD_ANGLE_NUMBER, this->nav_title->angle);
+ _x_stream_info_set(this->stream, XINE_STREAM_INFO_DVD_ANGLE_NUMBER, this->bdh->title->angle);
_x_stream_info_set(this->stream, XINE_STREAM_INFO_DVD_CHAPTER_NUMBER, 1);
- _x_stream_info_set(this->stream, XINE_STREAM_INFO_DVD_CHAPTER_COUNT, this->nav_title->chap_list.count);
- _x_stream_info_set(this->stream, XINE_STREAM_INFO_HAS_CHAPTERS, this->nav_title->chap_list.count>0);
+ _x_stream_info_set(this->stream, XINE_STREAM_INFO_DVD_CHAPTER_COUNT, this->bdh->title->chap_list.count);
+ _x_stream_info_set(this->stream, XINE_STREAM_INFO_HAS_CHAPTERS, this->bdh->title->chap_list.count>0);
- return next_clip(this);
+ return 1;
}
/*
@@ -209,33 +157,6 @@ static off_t bluray_plugin_read (input_plugin_t *this_gen, char *buf, off_t len)
if (!this || !this->bdh || len < 0)
return -1;
- if (this->bdh->aacs) {
-
- /*
- * Split large reads to aligned units
- */
-
- off_t todo = len;
- off_t block = MIN(todo, ALIGNED_UNIT_SIZE - (this->bdh->s_pos % ALIGNED_UNIT_SIZE));
-
- while (block > 0) {
- off_t result = bd_read(this->bdh, (unsigned char *)buf, block);
- if (result != block) {
- if (result < 0) {
- LOGMSG("ERROR: bd_read(aacs, %"PRId64") : got %"PRId64" !\n", block, result);
- return result;
- }
- return len - todo + MAX(0, result);
- }
- todo -= result;
- buf += result;
-
- block = MIN(todo, ALIGNED_UNIT_SIZE);
- }
-
- return len;
- }
-
off_t result = bd_read (this->bdh, (unsigned char *)buf, len);
if (result < 0)
@@ -279,38 +200,22 @@ static off_t bluray_plugin_seek (input_plugin_t *this_gen, off_t offset, int ori
{
bluray_input_plugin_t *this = (bluray_input_plugin_t *) this_gen;
- if (!this || !this->bdh || !this->nav_title)
+ if (!this || !this->bdh)
return -1;
/* convert relative seeks to absolute */
if (origin == SEEK_CUR) {
- offset = this->bdh->s_pos + offset;
+ offset = bd_tell(this->bdh) + offset;
}
else if (origin == SEEK_END) {
if (offset < this->bdh->s_size)
- offset = this->bdh->s_size - offset;
+ offset = bd_get_title_size(this->bdh) - offset;
else
offset = 0;
}
- /* clip seek point to nearest random access point */
-
- uint32_t in_pkt = offset / PKT_SIZE;
- uint32_t out_pkt = in_pkt;
- uint32_t out_time = 0;
- nav_packet_search(this->nav_title, in_pkt, &out_pkt, &out_time);
- lprintf("bluray_plugin_seek() seeking to %"PRId64" (packet %d)\n", offset, in_pkt);
- offset = (off_t)PKT_SIZE * (off_t)out_pkt;
- lprintf("Nearest random access point at %"PRId64" (packet %d)\n", offset, out_pkt);
-
- /* clip to aligned unit start */
-
- offset -= (offset % ALIGNED_UNIT_SIZE);
-
- /* seek */
-
- lprintf("bluray_plugin_seek() seeking to %lld (aligned unit)\n", (long long)offset);
+ lprintf("bluray_plugin_seek() seeking to %lld\n", (long long)offset);
return bd_seek (this->bdh, offset);
}
@@ -319,14 +224,14 @@ static off_t bluray_plugin_get_current_pos (input_plugin_t *this_gen)
{
bluray_input_plugin_t *this = (bluray_input_plugin_t *) this_gen;
- return this->bdh ? this->bdh->s_pos : 0;
+ return this->bdh ? bd_tell(this->bdh) : 0;
}
static off_t bluray_plugin_get_length (input_plugin_t *this_gen)
{
bluray_input_plugin_t *this = (bluray_input_plugin_t *) this_gen;
- return this->bdh ? this->bdh->s_size : -1;
+ return this->bdh ? bd_get_title_size(this->bdh) : -1;
}
static uint32_t bluray_plugin_get_blocksize (input_plugin_t *this_gen)
@@ -363,9 +268,9 @@ static int bluray_plugin_get_optional_data (input_plugin_t *this_gen, void *data
* - channel number can be mpeg-ts PID (0x1100 ... 0x11ff)
*/
case INPUT_OPTIONAL_DATA_AUDIOLANG:
- if (this->nav_title) {
+ if (this->bdh->title) {
int channel = *((int *)data);
- CLPI_PROG *prog = &this->nav_title->clip_list.clip->cl->program.progs[0];
+ CLPI_PROG *prog = &this->bdh->title->clip_list.clip->cl->program.progs[0];
int i, n = 0;
for (i=0 ; i < prog->num_streams; i++)
if (prog->streams[i].pid >= 0x1100 && prog->streams[i].pid < 0x1200) {
@@ -388,9 +293,9 @@ static int bluray_plugin_get_optional_data (input_plugin_t *this_gen, void *data
* - channel number can be mpeg-ts PID (0x1200 ... 0x12ff)
*/
case INPUT_OPTIONAL_DATA_SPULANG:
- if (this->nav_title) {
+ if (this->bdh->title) {
int channel = *((int *)data);
- CLPI_PROG *prog = &this->nav_title->clip_list.clip->cl->program.progs[0];
+ CLPI_PROG *prog = &this->bdh->title->clip_list.clip->cl->program.progs[0];
int i, n = 0;
for (i=0 ; i < prog->num_streams; i++)
if (prog->streams[i].pid >= 0x1200 && prog->streams[i].pid < 0x1300 &&
@@ -424,9 +329,6 @@ static void bluray_plugin_dispose (input_plugin_t *this_gen)
if (this->bdh)
bd_close(this->bdh);
- if (this->nav_title)
- nav_title_close(this->nav_title);
-
free (this->mrl);
free (this->disc_root);
@@ -482,7 +384,7 @@ static int bluray_plugin_open (input_plugin_t *this_gen)
title = 0;
if (main_title) {
if (sscanf(main_title, "%d.mpls", &title) != 1)
- title = 0;
+ title = -1;
lprintf("main title: %s (%d) \n", main_title, title);
} else {
LOGMSG("nav_find_main_title(%s) failed\n", this->disc_root);
@@ -507,19 +409,34 @@ static int bluray_plugin_open (input_plugin_t *this_gen)
/* select title */
- if (open_title(this, title) < 0)
+ int num_titles = bd_get_titles(this->bdh, TITLES_RELEVANT);
+ LOGMSG("%d relevant titles\n", num_titles);
+
+ if (open_title(this, title) <= 0 &&
+ open_title(this, 1) <= 0)
return -1;
/* jump to chapter */
if (chapter > 0) {
- uint32_t out_pkt = 0;
- NAV_CLIP *clip = nav_chapter_search(this->nav_title, chapter, &out_pkt);
- bluray_plugin_seek(&this->input_plugin, (off_t)(clip->title_pkt + out_pkt) * PKT_SIZE, SEEK_SET);
-
+ bd_seek_chapter(this->bdh, chapter);
_x_stream_info_set(this->stream, XINE_STREAM_INFO_DVD_CHAPTER_NUMBER, chapter);
}
+ uint64_t rate = this->bdh->title->packets * UINT64_C(192) * UINT64_C(8) // bits
+ * INT64_C(45000) // tick is 1/45000s
+ / (uint64_t)(this->bdh->title->duration);
+ _x_stream_info_set(this->stream, XINE_STREAM_INFO_BITRATE, rate);
+
+ int krate = (int)(rate / UINT64_C(1024));
+ int s = this->bdh->title->duration / 45000;
+ int h = s / 3600; s -= h*3600;
+ int m = s / 60; s -= m*60;
+ int f = this->bdh->title->duration % 45000; f = f * 1000 / 45000;
+ LOGMSG("BluRay stream: length: %d:%d:%d.%03d\n"
+ " bitrate: %d.%03d Mbps\n\n",
+ h, m, s, f, krate/1024, (krate%1024)*1000/1024);
+
return 1;
}