Re: [PATCH SBC 1/2] sbc: Add sbc_init_a2dp

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Hi Luiz,

> This adds sbc_init_a2dp that can be used to convert A2DP configuration to
> the internal representation since they are not binary compatible.
> ---
> sbc/sbc.c | 138 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
> sbc/sbc.h |   1 +
> 2 files changed, 139 insertions(+)
> 
> diff --git a/sbc/sbc.c b/sbc/sbc.c
> index c589217..4483074 100644
> --- a/sbc/sbc.c
> +++ b/sbc/sbc.c
> @@ -57,6 +57,55 @@
> #define MSBC_SYNCWORD	0xAD
> #define MSBC_BLOCKS	15
> 
> +#define A2DP_SAMPLING_FREQ_16000		(1 << 3)
> +#define A2DP_SAMPLING_FREQ_32000		(1 << 2)
> +#define A2DP_SAMPLING_FREQ_44100		(1 << 1)
> +#define A2DP_SAMPLING_FREQ_48000		1

Use (1 << 0) here and let the compiler optimize it.

> +
> +#define A2DP_CHANNEL_MODE_MONO			(1 << 3)
> +#define A2DP_CHANNEL_MODE_DUAL_CHANNEL		(1 << 2)
> +#define A2DP_CHANNEL_MODE_STEREO		(1 << 1)
> +#define A2DP_CHANNEL_MODE_JOINT_STEREO		1
> +
> +#define A2DP_BLOCK_LENGTH_4			(1 << 3)
> +#define A2DP_BLOCK_LENGTH_8			(1 << 2)
> +#define A2DP_BLOCK_LENGTH_12			(1 << 1)
> +#define A2DP_BLOCK_LENGTH_16			1
> +
> +#define A2DP_SUBBANDS_4				(1 << 1)
> +#define A2DP_SUBBANDS_8				1
> +
> +#define A2DP_ALLOCATION_SNR			(1 << 1)
> +#define A2DP_ALLOCATION_LOUDNESS		1
> +
> +#if __BYTE_ORDER == __LITTLE_ENDIAN
> +
> +typedef struct {
> +	uint8_t channel_mode:4;
> +	uint8_t frequency:4;
> +	uint8_t allocation_method:2;
> +	uint8_t subbands:2;
> +	uint8_t block_length:4;
> +	uint8_t min_bitpool;
> +	uint8_t max_bitpool;
> +} __attribute__ ((packed)) a2dp_sbc_t;

If these are internal anyway, then typedef is not needed. Just use a plain packed struct.
 
> +
> +#elif __BYTE_ORDER == __BIG_ENDIAN
> +
> +typedef struct {
> +	uint8_t frequency:4;
> +	uint8_t channel_mode:4;
> +	uint8_t block_length:4;
> +	uint8_t subbands:2;
> +	uint8_t allocation_method:2;
> +	uint8_t min_bitpool;
> +	uint8_t max_bitpool;
> +} __attribute__ ((packed)) a2dp_sbc_t;
> +
> +#else
> +#error "Unknown byte order"
> +#endif
> +
> /* This structure contains an unpacked SBC frame.
>    Yes, there is probably quite some unused space herein */
> struct sbc_frame {
> @@ -1046,6 +1095,95 @@ SBC_EXPORT int sbc_init_msbc(sbc_t *sbc, unsigned long flags)
> 	return 0;
> }
> 
> +SBC_EXPORT int sbc_init_a2dp(sbc_t *sbc, unsigned long flags, void *data)
> +{

const void *data. I think we should also add a size_t len to it.

Using the general “data” is a bit too generic. What is it actually called in the A2DP PDU anyway?

> +	a2dp_sbc_t *a2dp = data;
> +	int err;
> +
> +	err = sbc_init(sbc, flags);
> +	if (err < 0)
> +		return err;
> +
> +	switch (a2dp->frequency) {
> +        case A2DP_SAMPLING_FREQ_16000:

Spaces?

> +		sbc->frequency = SBC_FREQ_16000;
> +		break;
> +	case A2DP_SAMPLING_FREQ_32000:
> +		sbc->frequency = SBC_FREQ_32000;
> +		break;
> +	case A2DP_SAMPLING_FREQ_44100:
> +		sbc->frequency = SBC_FREQ_44100;
> +		break;
> +	case A2DP_SAMPLING_FREQ_48000:
> +		sbc->frequency = SBC_FREQ_48000;
> +		break;
> +	default:
> +		goto failed;
> +	}
> +
> +	switch (a2dp->channel_mode) {
> +	case A2DP_CHANNEL_MODE_MONO:
> +		sbc->mode = SBC_MODE_MONO;
> +		break;
> +	case A2DP_CHANNEL_MODE_DUAL_CHANNEL:
> +		sbc->mode = SBC_MODE_DUAL_CHANNEL;
> +		break;
> +	case A2DP_CHANNEL_MODE_STEREO:
> +		sbc->mode = SBC_MODE_STEREO;
> +		break;
> +	case A2DP_CHANNEL_MODE_JOINT_STEREO:
> +		sbc->mode = SBC_MODE_JOINT_STEREO;
> +		break;
> +	default:
> +		goto failed;
> +	}
> +
> +	switch (a2dp->allocation_method) {
> +	case A2DP_ALLOCATION_SNR:
> +		sbc->allocation = SBC_AM_SNR;
> +		break;
> +	case A2DP_ALLOCATION_LOUDNESS:
> +		sbc->allocation = SBC_AM_LOUDNESS;
> +		break;
> +	default:
> +		goto failed;
> +	}
> +
> +	switch (a2dp->subbands) {
> +	case A2DP_SUBBANDS_4:
> +		sbc->subbands = SBC_SB_4;
> +		break;
> +        case A2DP_SUBBANDS_8:

Spaces?

> +		sbc->subbands = SBC_SB_8;
> +		break;
> +	default:
> +		goto failed;
> +	}
> +
> +	switch (a2dp->block_length) {
> +	case A2DP_BLOCK_LENGTH_4:
> +		sbc->blocks = SBC_BLK_4;
> +		break;
> +	case A2DP_BLOCK_LENGTH_8:
> +		sbc->blocks = SBC_BLK_8;
> +		break;
> +	case A2DP_BLOCK_LENGTH_12:
> +		sbc->blocks = SBC_BLK_12;
> +		break;
> +	case A2DP_BLOCK_LENGTH_16:
> +		sbc->blocks = SBC_BLK_16;
> +		break;
> +	default:
> +		goto failed;
> +	}
> +
> +	return 0;
> +
> +failed:
> +	sbc_finish(sbc);
> +	return -EINVAL;
> +}
> +
> SBC_EXPORT ssize_t sbc_parse(sbc_t *sbc, const void *input, size_t input_len)
> {
> 	return sbc_decode(sbc, input, input_len, NULL, 0, NULL);
> diff --git a/sbc/sbc.h b/sbc/sbc.h
> index 5f8a1fc..1d1c5a1 100644
> --- a/sbc/sbc.h
> +++ b/sbc/sbc.h
> @@ -84,6 +84,7 @@ typedef struct sbc_struct sbc_t;
> int sbc_init(sbc_t *sbc, unsigned long flags);
> int sbc_reinit(sbc_t *sbc, unsigned long flags);
> int sbc_init_msbc(sbc_t *sbc, unsigned long flags);
> +int sbc_init_a2dp(sbc_t *sbc, unsigned long flags, void *data);
> 
> ssize_t sbc_parse(sbc_t *sbc, const void *input, size_t input_len);

Regards

Marcel

--
To unsubscribe from this list: send the line "unsubscribe linux-bluetooth" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html




[Index of Archives]     [Bluez Devel]     [Linux Wireless Networking]     [Linux Wireless Personal Area Networking]     [Linux ATH6KL]     [Linux USB Devel]     [Linux Media Drivers]     [Linux Audio Users]     [Linux Kernel]     [Linux SCSI]     [Big List of Linux Books]

  Powered by Linux