MidiUnavailableException in Java on Android - java

I am writing a program in Java for android. When calling the getSequencer method, I get a MidiUnavailableException exception.
When executing this code :
MidiDevice.Info[] devices = MidiSystem.getMidiDeviceInfo();
if (devices.length == 0) {
System.out.println("No MIDI devices found");
} else {
for (MidiDevice.Info dev : devices) {
System.out.println(dev);
}
}
I got the "No MIDI devices found". I realized that you can solve this problem by installing soundbank at this link:https://www.oracle.com/java/technologies/sound-banks.html
But it describes the installation method for Windows. And how to install soundbank for android?

Related

Can we open channel without AID and control the power of embedded SE?

We are now developing a payment card with NXP NQ220 (has embedded SE, called eSE) on Android N. The platform is MTK. Now, we can interact with eSE using OMA (using org.simalliance.openmobileapi.jar). It works as expected.
I was wondering if there is any ways to open channel in session without AID? Besides, is there any ways to control the power of eSE(power-on and power-off) and reset eSE in some situations?
My investigation as follows:
About open channel without AID, I have found following sentences in page 16 of Open Mobile API specification V3.
(h)Method: Channel openLogicalChannel(byte[] aid, Byte P2)
Open a logical channel with the SE, selecting the applet represented by the >given AID. If the AID is null, which means no applet is to be selected on >this channel, the default applet is used. It's up to the SE to choose which >logical channel will be used.
However, if we set aid to null in openLogicalChannel(byte[] aid), following exception will be shows. What happens about it? Is the default applet or eSE have problems?
01-30 01:06:39.941 V/SmartcardService( 2587): OpenLogicalChannel Exception: Access Control Enforcer: no APDU access allowed!
01-30 01:06:39.947 E/SeControlClient( 3239): Error occured:
01-30 01:06:39.947 E/SeControlClient( 3239): java.lang.SecurityException: Access Control Enforcer: no APDU access allowed!
01-30 01:06:39.947 E/SeControlClient( 3239): at org.simalliance.openmobileapi.SEService.checkForException(SEService.java:255)
01-30 01:06:39.947 E/SeControlClient( 3239): at org.simalliance.openmobileapi.Session.openLogicalChannel(Session.java:295)
It seems there is no method in OMA to reset eSE. But I found reset() method in INxpNfcAdapterExtras. However, when I use INxpNfcAdapterExtras.reset(), it always return false. Following codes is how we get INxpNfcAdapterExtras.
private INxpNfcAdapterExtras getNxpNfcAdapterExtras() {
if (mNfcAdapter != null) {
try {
INxpNfcAdapter nxpNfcAdapter =
mNfcAdapter.getService().getNxpNfcAdapterInterface();
return nxpNfcAdapter.getNxpNfcAdapterExtrasInterface();
} catch (Exception e) {
Log.e(LOGTAG, "Exception occured:", e);
}
} else {
Log.e(LOGTAG, "Please initialize NfcAdapter first.");
}
return null;
}
About control the power of eSE, is it related to the platform? Can you give me some suggestions? Thank you very much.
Dont known
To access SE functions your application must be execute with owner of android device.
You could check this in : https://github.com/NXPNFCLinux/android_nxp-nci/blob/1d95fe24334fa12c9d9eccd1141f8739972c4288/aosp/packages/apps/Nfc/src/com/android/nfc/NfcService.java
The reset method check permission before:
public boolean reset(String pkg) throws RemoteException {
NfcService.this.enforceNfceeAdminPerm(pkg);
Bundle result;
boolean stat = false;
try {
stat = _nfcEeReset();
result = writeNoException();
} catch (IOException e) {
result = writeEeException(EE_ERROR_IO, e.getMessage());
}
Log.d(TAG,"reset" + stat);
return stat;
}
The check permission method:
public void enforceNfceeAdminPerm(String pkg) {
if (pkg == null) {
throw new SecurityException("caller must pass a package name");
}
NfcPermissions.enforceUserPermissions(mContext);
if (!mNfceeAccessControl.check(Binder.getCallingUid(), pkg)) {
throw new SecurityException(NfceeAccessControl.NFCEE_ACCESS_PATH +
" denies NFCEE access to " + pkg);
}
if (UserHandle.getCallingUserId() != UserHandle.USER_OWNER) {
throw new SecurityException("only the owner is allowed to call SE APIs");
}
}
To execute your app with device owner, you could follow my anwser here:
Device Admin API, how to be a device owner?
I'm not sure about what you mean "control the power of eSE". If it's on/off eSE, then eSE is integrated with NFC chip so if you disable NFC in Android eSE will be power off.
I have found another way to solve this issue. It used NXP's own class NxpNfcAdapterExtrasService.
1.I still don't know why the exception happens when we open channel use the default Applet(without AID). But, with the method in NxpNfcAdapterExtrasService, we can establish connection with eSE.
2.About the second question. The codes is right but the way of how to use INxpNfcAdapterExtras.reset() is wrong. This method will return true only when you do something with eSE. Like transmit and execute APDU commands. So you can use this method when you want to disconnect the connection with eSE.
3.About the third question, I don't know whether the openUicc()/closeUicc() method can control the eSE power. But, it seems this two method works as expected.

Error in using usb4java

followed the instruction as stated here . Added the properties file in my root project and libraries on the project class path. When i run the project, it returns.
Exception in thread "main" javax.usb.UsbPlatformException: Class org.usb4java.javax.Services does not have the needed constructor
at javax.usb.UsbHostManager.initialize(UsbHostManager.java:46)
at javax.usb.UsbHostManager.getUsbServices(UsbHostManager.java:24)
at usbfinderdemo.UsbFinderDemo.main(UsbFinderDemo.java:30)
Don't know what might be wrong. Thinking i might not be using the right .jar file of usb4java, but i'm not certain yet as the code does not show any error at all.
Code Snippet
UsbServices services = UsbHostManager.getUsbServices();//the line that throws the error.
UsbHub rootHub = services.getRootUsbHub();
List<UsbDevice> devices = rootHub.getAttachedUsbDevices();
if (devices.size() > 0) {
System.out.println("USB devices found.");
} else {
System.out.println("No USB devices found.");
}
for (UsbDevice device : devices) {
System.out.println("\tProduct String " + device.getProductString());
System.out.println("\tManufacturer String " + device.getManufacturerString());
System.out.println("\tSerial Number " + device.getSerialNumberString());
}

Bluetooth communication between Processing Desktop and Android(Not Processing)

What I'm doing is communication between
Desktop(Windows 8) Processing(2.2.1) Application <---- Android application(Not made by Processing, it's made on Android Studio)
I need to send data to desktop from android application (one side communication).
From android..
First, I'm getting already paired device. It means that before executing both application, I will pair desktop and android device already.
Bluetooth connection and sending outstream is on child thread.
Set<BluetoothDevice> pairedDevices = btAdapter.getBondedDevices();
if (pairedDevices.size() > 0) {
for (BluetoothDevice device : pairedDevices) {
Log.i(TAG, device.getName() + "\n" + device.getAddress());
targetDevice = device;
break;
}
}else{
Log.i(TAG, "No paired device found!");
}
And then, I connect it
BluetoothSocket tmp = null;
// Get a BluetoothSocket for a connection with the
// given BluetoothDevice
try {
tmp = targetDevice.createRfcommSocketToServiceRecord(MY_UUID);
Method m = targetDevice.getClass().getMethod("createRfcommSocket", new Class[]{int.class});
tmp = (BluetoothSocket) m.invoke(targetDevice, 1);
} catch (Exception e) {
Log.e(TAG, "create() failed", e);
}
btSocket = tmp;
if (btSocket != null){
// Socket is created
// try to connect the socket
BluetoothConnectionThread thread = new BluetoothConnectionThread(btSocket);
thread.start();
}
From logcat(Log.i), I can see connection is successfully established. It seems that there is no problem on android side.
I'm using Serial Port Protocol UUID which is
private static final UUID MY_UUID = UUID.fromString("00001101-0000-1000-8000-00805f9b34fb");
And from Android side, it's completely ready to write any byte[].. and when I press dummy button on android, device sends dummy bytes to outputstream. I think it has no problem here on Android side..
Now, on desktop processing(Windows 8, processing 2.2.1 - I HAVE TO USE processing 2.0, there is no other option for some reason.), I have no any clue what I have to now.. I searched in google a lot but I could not find any clue. Now, I'm trying to use processing Serial library like
println(Serial.list());
but it gives nothing... So, I tried to initialize Serial object by
Serial port = new Serial(this, "/dev/rfcomm0", 115200);
but it gives error
Error opening serial port /dev/rfcomm0:Port busy
Is there any other way to read socket buffer(instream) which comes from Android on processing desktop?
I am sure that this is not bluetooth driver issue because I installed the recentest driver for my desktop(Qualcomm Atheros AR3012 Bluetooth 4.0 + HS)
Just for reference..desktop is actually laptop with bluetooth(ASUS UX21E) and Android device is Galaxy Tab S(267.2mm, Octa-Core 2560x1600).
I think I have not enough knowledge about bluetooth... Please lead me to some way...

MediaRecorder - setOrientationHint() exception/fail

I've been trying to fix this problem with MediaRecorder video Rotation on and off for weeks. I cannot get the line setOrientationHint(90) to work on a physical Samsung Galaxy S1 running Android 2.3.3 (SDK 10). This should run fine on anything above SDK 9.
When I call setOrientationHint(90) I get an exception : setParameters(video-param-rotation-angle-degrees=90) failed. Detailed error details below.
As a result I'm forced to check SDK and only call setOrientationHint() if SDK>10. ie, this code works fine on all other SDK versions above 10 which I have tested. I have tested on Samsung Galaxy Nexus running 4.2.2 and works fine.
Here is my code:
(cut down to show order of calls to MediaRecorder)
mCamera = getCameraInstance();
mCamera.setPreviewDisplay(holder);
mMediaRecorder = new MediaRecorder();
mMediaRecorder.setOrientationHint(90);
// Step 1: Unlock and set camera to MediaRecorder
mCamera.unlock();
mMediaRecorder.setCamera(mCamera);
// Step 2: Set sources
mMediaRecorder.setAudioSource(MediaRecorder.AudioSource.CAMCORDER);
mMediaRecorder.setVideoSource(MediaRecorder.VideoSource.CAMERA);
// Step 3: recording setup
mMediaRecorder.setOutputFormat(MediaRecorder.OutputFormat.MPEG_4);
mMediaRecorder.setVideoSize(720,480);
mMediaRecorder.setVideoFrameRate(15);
mMediaRecorder.setVideoEncoder(MediaRecorder.VideoEncoder.H264);
mMediaRecorder.setAudioEncoder(MediaRecorder.AudioEncoder.AAC);
// Step 4: Set output file
currentOutputFileName = DIRECTORY_PATH + "zzzz"+ iCount +".mp4";
mFile = new File(currentOutputFileName);
mMediaRecorder.setOutputFile(mFile.getAbsolutePath());
// Step 4.1: Set recording length
mMediaRecorder.setMaxDuration(10000);
// Step 5: Set the preview output
mMediaRecorder.setPreviewDisplay(cameraView.getHolder().getSurface());
// Step 6: Prepare configured MediaRecorder
mMediaRecorder.prepare();
Has anyone had this problem? I can't find anyone else is experiencing this and I can't believe thats the case. Is it possible its just a Australian Samsung Galaxy S1 running 2.3.3 issue?
I've seen references to people having problems where that line runs but with the actual video does not rotate but I actually receive an Exception - the line doesn't run at all. I've checked and rechecked the command order and it seems fine. I think what is most important is that the setOrientationHint() command occurs before mediaRecorder.prepare()
Here is the Error:
AuthorDriver::setParameter() unrecognized key "video-param-rotation-angle-degrees"
setParameter(video-param-rotation-angle-degrees = 90) failed with result -5
Ln 1047 handleSetParameters("video-param-rotation-angle-degrees=90") error
Command (12) failed
setParameters(video-param-rotation-angle-degrees=90) failed: -2147483648
Shutting down VM
threadid=1: thread exiting with uncaught exception (group=0x40015578)
FATAL EXCEPTION: main
java.lang.RuntimeException: setParameter failed.
at android.media.MediaRecorder.setParameter(Native Method)
at android.media.MediaRecorder.setOrientationHint(MediaRecorder.java:341)
at com.on3x.emergency.Recorder.prepareVideoRecorder(Recorder.java:196)
at com.on3x.emergency.Recorder.startRecording(Recorder.java:90)
at com.on3x.emergency.GUI.RecordActivity$1.onClick(RecordActivity.java:86)
at android.view.View.performClick(View.java:2538)
at android.view.View$PerformClick.run(View.java:9152)
at android.os.Handler.handleCallback(Handler.java:587)
at android.os.Handler.dispatchMessage(Handler.java:92)
at android.os.Looper.loop(Looper.java:123)
at android.app.ActivityThread.main(ActivityThread.java:3687)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:507)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:842)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:600)
at dalvik.system.NativeStart.main(Native Method)
Force finishing activity com.on3x.emergency/.GUI.RecordActivity
Dumpstate > /data/log/dumpstate_app_error
If anyone can give ANY help it would be much appreciated. For now I've had to tell our client that its not something I can fix at this moment and Video will have to be sideways.
Is there another way of rotating videos? Basically my app records videos and uploads them to the server. At the moment this 2.3.3 phone cannot rotate the video so its uploaded sideways
Cheers
Edit:
This is the code I now have in place. As suggested by Ashish Gupta, AuthorDriver does not contain the appropriate param on Samsung Galaxy S1 (australian model) running 2.3.3
if (android.os.Build.VERSION.SDK_INT>=9) {
// attempt to rotate the video 90 degrees.
try {
mMediaRecorder.setOrientationHint(90);
Utils.logLine("orientation rotated 90", this, Utils.LOG_TYPE_DEBUG);
} catch (Exception e) {
Utils.logLine("error trying setOrientationHint"+ e.getMessage(), this, Utils.LOG_TYPE_ERROR, e);
e.printStackTrace();
}
} else {
Utils.logLine("orientation set skipped ", this, Utils.LOG_TYPE_DEBUG);
}
Note: Utils.logLine is simply a Utilility function I have for printing debug and error statements to log. Hopefully that might help someone else...
Looking at the logs you have attached, it seems that Samsung Galaxy S1 running Android 2.3.3 does not support setOrientationHint.
This is the code from AuthorDriver.cpp
PVMFStatus AuthorDriver::setParameter(
const String8& key, const String8& value) {
if (key == "max-duration") {
int64_t max_duration_ms;
if (safe_strtoi64(value.string(), &max_duration_ms)) {
return setMaxDurationOrFileSize(
max_duration_ms, true /* limit_is_duration */);
}
} else if (key == "max-filesize") {
int64_t max_filesize_bytes;
if (safe_strtoi64(value.string(), &max_filesize_bytes)) {
return setMaxDurationOrFileSize(
max_filesize_bytes, false /* limit is filesize */);
}
} else if (key == "audio-param-sampling-rate") {
int64_t sampling_rate;
if (safe_strtoi64(value.string(), &sampling_rate)) {
return setParamAudioSamplingRate(sampling_rate);
}
} else if (key == "audio-param-number-of-channels") {
int64_t number_of_channels;
if (safe_strtoi64(value.string(), &number_of_channels)) {
return setParamAudioNumberOfChannels(number_of_channels);
}
} else if (key == "audio-param-encoding-bitrate") {
int64_t audio_bitrate;
if (safe_strtoi64(value.string(), &audio_bitrate)) {
return setParamAudioEncodingBitrate(audio_bitrate);
}
} else if (key == "video-param-encoding-bitrate") {
int64_t video_bitrate;
if (safe_strtoi64(value.string(), &video_bitrate)) {
return setParamVideoEncodingBitrate(video_bitrate);
}
}
// Return error if the key wasnt found
LOGE("AuthorDriver::setParameter() unrecognized key \"%s\"", key.string());
return PVMFErrArgument;
}
The key video-param-rotation-angle-degrees is not supported on Samsung Galaxy S1 aith Android 2.3.3
You can compare the logs between Nexus 4.2.2 and S1 2.3.3 and see if you see any noticeable difference.

BlueCove Bluetooth Device Discovery

I've built and ran the RemoteDeviceDiscovery sample project for BlueCove 2.1.1. The program will discover all discoverable bluetooth devices but it will also report in deviceDiscovered() devices that were once paired before.
Is there a way to ONLY discover devices around you (like in Android)? The code below returns BOTH discovered devices and paired devices...
public void deviceDiscovered(RemoteDevice btDevice, DeviceClass cod) {
System.out.println("Device " + btDevice.getBluetoothAddress() + " found");
devicesDiscovered.addElement(btDevice);
try {
System.out.println(" name " + btDevice.getFriendlyName(false));
} catch (IOException cantGetDeviceName) {
}
}
Yes - use http://bluecove.org/bluecove/apidocs/javax/bluetooth/RemoteDevice.html#isTrustedDevice() to filter unpaired devices (or paired devices if you wish to).

Categories

Resources