Commit Graph

370 Commits

Author SHA1 Message Date
Romain Vimont
ff82852f28 Print info logs to stdout
All server logs were printed to stdout, while all client logs were
printed to stderr.

Instead, use stderr for warnings and errors, stdout for the others:
 - stdout: verbose, debug, info
 - stderr: warn, error
2023-03-09 19:21:33 +01:00
Romain Vimont
9f8f312c50 Print server logs and newline in one call
System.out.println() first prints the message, then the new line.
Between these two calls, the client might print a message, breaking
formatting.

Instead, call System.out.print() with '\n' appended to the message.
2023-03-09 19:21:33 +01:00
Romain Vimont
2611f7f0ca Add raw audio recorder
Add an alternative AudioRecorder to stream raw packets without encoding.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:33 +01:00
Romain Vimont
81838f1678 Extract async processor interface
On the server side, several components are started, stopped and joined.
Extract an interface to handle them generically.

This will help to support both encoded and raw audio stream, because
they will be two different concrete components, but implementing the
same interface.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:32 +01:00
Romain Vimont
5fff56ee6f Extract audio capture
The audio capture was implemented in AudioEncoder.

In order to reuse it without encoding, extract it to a separate class.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:32 +01:00
Simon Chan
47f67412e4 Add workaround to capture audio on Android 11
On Android 11, it is possible to start the capture only when the running
app is in foreground. But scrcpy is not an app, it's a Java application
started from shell.

As a workaround, start an existing Android shell existing activity just
to start the capture, then close it immediately.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>

Co-authored-by: Romain Vimont <rom@rom1v.com>
Signed-off-by: Romain Vimont <rom@rom1v.com>
2023-03-09 19:21:24 +01:00
Romain Vimont
4c24ea50ed Log display sizes in display list
This is more convenient than just the display id alone.
2023-03-09 19:21:22 +01:00
Romain Vimont
eb39365737 Add --list-displays
Add an option to list the device displays properly.
2023-03-09 19:21:21 +01:00
Romain Vimont
46169618a5 Move log message helpers to LogUtils
This class will also contain other log helpers.
2023-03-09 19:21:21 +01:00
Romain Vimont
1a3c61a77b Quit on audio configuration failure
When audio capture fails on the device, scrcpy continues mirroring the
video stream. This allows to enable audio by default only when
supported.

However, if an audio configuration occurs (for example the user
explicitly selected an unknown audio encoder), this must be treated as
an error and scrcpy must exit.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:21 +01:00
Romain Vimont
fe9166a88c Add --list-encoders
Add an option to list the device encoders properly.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:21 +01:00
Romain Vimont
0b24cb930c Add --audio-encoder
Similar to --video-encoder, but for audio.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:21 +01:00
Romain Vimont
8edb1c8eef Extract unknown encoder error message
This will allow to reuse the same code for audio encoder selection.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:20 +01:00
Romain Vimont
775789e50b Add --audio-codec-options
Similar to --video-codec-options, but for audio.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:20 +01:00
Romain Vimont
b3641dc025 Extract application of codec options
This will allow to reuse the same code for audio codec options.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:20 +01:00
Romain Vimont
5c24f32651 Add support for AAC audio codec
Add option --audio-codec=aac.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:20 +01:00
Romain Vimont
7b0977c7d9 Add --audio-codec
Introduce the selection mechanism. Alternative codecs will be added
later.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:20 +01:00
Romain Vimont
b992191572 Add --audio-bit-rate
Add an option to configure the audio bit-rate.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:20 +01:00
Romain Vimont
a6de3e67b2 Disable MethodLength checkstyle on createOptions()
This method will grow as needed to initialize options.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:20 +01:00
Romain Vimont
94a14e7fd0 Rename --encoder to --video-encoder
This prepares the introduction of --audio-encoder.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:19 +01:00
Romain Vimont
bf3b1c70df Rename --codec-options to --video-codec-options
This prepares the introduction of --audio-codec-options.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:19 +01:00
Romain Vimont
4950d5c846 Rename --bit-rate to --video-bit-rate
This prepares the introduction of --audio-bit-rate.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:19 +01:00
Romain Vimont
3f98478ad7 Rename --codec to --video-codec
This prepares the introduction of --audio-codec.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:19 +01:00
Romain Vimont
7daebaadae Disable audio before Android 11
The permission "android.permission.RECORD_AUDIO" has been added for
shell in Android 11.

Moreover, on lower versions, it may make the server segfault on the
device (happened on a Nexus 5 with Android 6.0.1).

Refs <4feeee8891%5E%21/>
PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:19 +01:00
Romain Vimont
2bc9b687db Disable audio on initialization error
By default, audio is enabled (--no-audio must be explicitly passed to
disable it).

However, some devices may not support audio capture (typically devices
below Android 11, or Android 11 when the shell application is not
foreground on start).

In that case, make the server notify the client to dynamically disable
audio forwarding so that it does not wait indefinitely for an audio
stream.

Also disable audio on unknown codec or missing decoder on the
client-side, for the same reasons.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:19 +01:00
Romain Vimont
aff7b7f26a Extract OPUS extradata
For OPUS codec, FFmpeg expects the raw extradata, but MediaCodec wraps
it in some structure.

Fix the config packet to send only the raw extradata.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:18 +01:00
Romain Vimont
160de07e8a Use a streamer to send the audio stream
Send each encoded audio packet using a streamer.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:18 +01:00
Romain Vimont
805d85dc3b Encode recorded audio on the device
For now, the encoded packets are just logged into the console.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:17 +01:00
Romain Vimont
29c04995b4 Make streamer more generic
Expose a method to write a packet from raw metadata (without
BufferInfo).
2023-03-09 19:21:17 +01:00
Simon Chan
03a553f590 Capture device audio
Create an AudioRecorder to capture the audio source REMOTE_SUBMIX.

For now, the captured packets are just logged into the console.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>

Co-authored-by: Romain Vimont <rom@rom1v.com>
Signed-off-by: Romain Vimont <rom@rom1v.com>
2023-03-09 19:21:17 +01:00
Simon Chan
e2aa3cca52 Add a new socket for audio stream
When audio is enabled, open a new socket to send the audio stream from
the device to the client.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>

Co-authored-by: Romain Vimont <rom@rom1v.com>
Signed-off-by: Romain Vimont <rom@rom1v.com>
2023-03-09 19:21:17 +01:00
Simon Chan
de1dfae169 Add --no-audio option
Audio will be enabled by default (when supported). Add an option to
disable it.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>

Co-authored-by: Romain Vimont <rom@rom1v.com>
Signed-off-by: Romain Vimont <rom@rom1v.com>
2023-03-09 19:21:17 +01:00
Romain Vimont
b6a8b6f91a Use FakeContext for Application instance
This will expose the correct package name and UID to the application
context.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:17 +01:00
Romain Vimont
2346148827 Use shell package name for workarounds
For consistency.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:17 +01:00
Romain Vimont
27918a501c Use ROOT_UID from FakeContext
Remove USER_ID from ServiceManager, and replace it by a constant in
FakeContext.

This is the same as android.os.Process.ROOT_UID, but this constant has
been introduced in API 29.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:17 +01:00
Romain Vimont
631801ce3e Use PACKAGE_NAME from FakeContext
Remove duplicated constant.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:16 +01:00
Romain Vimont
884d0ec246 Use AttributionSource from FakeContext
FakeContext already provides an AttributeSource instance.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>

Co-authored-by: Simon Chan <1330321+yume-chan@users.noreply.github.com>
2023-03-09 19:21:16 +01:00
Simon Chan
db0c5bc066 Add a fake Android Context
Since scrcpy-server is not an Android application (it's a java
executable), it has no Context.

Some features will require a Context instance to get the package name
and the UID. Add a FakeContext for this purpose.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>

Co-authored-by: Romain Vimont <rom@rom1v.com>
Signed-off-by: Romain Vimont <rom@rom1v.com>
2023-03-09 19:21:16 +01:00
Romain Vimont
681fde542d Improve error message for unknown encoder
The provided encoder name depends on the selected codec. Improve the
error message and the suggestions.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:16 +01:00
Romain Vimont
fb12118190 Rename "codec" variable to "mediaCodec"
This will allow to use "codec" for the Codec type.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:16 +01:00
Romain Vimont
a1d84709ca Make streamer independent of codec type
Rename VideoStreamer to Streamer, and extract a Codec interface which
will also support audio codecs.

PR #3757 <https://github.com/Genymobile/scrcpy/pull/3757>
2023-03-09 19:21:16 +01:00
Romain Vimont
77277238b3 Pass all args to ScreenEncoder constructor
There is no good reason to pass some of them in the constructor and some
others as parameters of the streamScreen() method.
2023-03-09 19:21:16 +01:00
Romain Vimont
b9ee7c5852 Move screen encoder initialization
This prepares further refactors.
2023-03-09 19:21:16 +01:00
Romain Vimont
ec6641b519 Write streamer header from ScreenEncoder
The screen encoder is responsible for writing data to the video
streamer.
2023-03-09 19:21:15 +01:00
Romain Vimont
8fb9c28c59 Use VideoStreamer directly from ScreenEncoder
The Callbacks interface notifies new packets. But in addition, the
screen encoder will need to write headers on start.

We could add a function onStart(), but for simplicity, just remove the
interface, which brings no value, and call the streamer directly.

Refs 87972e2022
2023-03-09 19:21:15 +01:00
Romain Vimont
836f0042af Simplify error handling on socket creation
On any error, all previously opened sockets must be closed.

Handle these errors in a single catch-block. Currently, there are only 2
sockets, but this will simplify even more with more sockets.

Note: this commit is better displayed with --ignore-space-change (-b).
2023-03-09 19:21:15 +01:00
Romain Vimont
4d719da424 Do not print stacktraces when unnecessary
User-friendly error messages are printed on specific configuration
exceptions. In that case, do not print the stacktrace.

Also handle the user-friendly error message directly where the error
occurs, and print multiline messages in a single log call, to avoid
confusing interleaving.
2023-03-09 19:21:13 +01:00
Romain Vimont
14a85fd61e Silence lint warning about constant in API 29
MediaFormat.MIMETYPE_VIDEO_AV1 has been added in API 29, but it is not
a problem to inline the constant in older versions.
2023-03-03 11:13:48 +01:00
Romain Vimont
5bf52a98ed Remove manifest package name
As reported by gradle:

> Setting the namespace via a source AndroidManifest.xml's package
> attribute is deprecated.
>
> Please instead set the namespace (or testNamespace) in the module's
> build.gradle file, as described here:
> https://developer.android.com/studio/build/configure-app-module#set-namespace
2023-03-03 11:13:48 +01:00
Romain Vimont
ebecbe6bc6 Fix inconsistent quotes
The encoder name started with a simple quote but ended with a
double quote. Use a single quote for both.
2023-02-19 16:18:19 +01:00