tinyalsa: pcm: open pcm driver in non blocking mode

- in current implementation pcm open call is blocking hence if pcm_open
  is done on same driver twice second pcm open will get blocked till
  first instance of the PCM driver is not released.
  In times this will result in deadlock.

- fix this issue by making PCM open in non-blocking mode.

- after pcm open is successful, in non-blocking mode, change the device
  mode to blocking again to make sure rest of the operation on the
  driver, like read / write calls, are always called in blocking mode.

Also fix jump to wrong label in case of failure before mmap().

Bug: 29865791
Bug: 30388410
Change-Id: I95c0ad8456e6c2bb3bfb48813e1db75cdef387f8
diff --git a/pcm.c b/pcm.c
index 394faba..78e1cea 100644
--- a/pcm.c
+++ b/pcm.c
@@ -855,12 +855,18 @@
              flags & PCM_IN ? 'c' : 'p');
 
     pcm->flags = flags;
-    pcm->fd = open(fn, O_RDWR);
+    pcm->fd = open(fn, O_RDWR|O_NONBLOCK);
     if (pcm->fd < 0) {
         oops(pcm, errno, "cannot open device '%s'", fn);
         return pcm;
     }
 
+    if (fcntl(pcm->fd, F_SETFL, fcntl(pcm->fd, F_GETFL) &
+              ~O_NONBLOCK) < 0) {
+        oops(pcm, errno, "failed to reset blocking mode '%s'", fn);
+        goto fail_close;
+    }
+
     if (ioctl(pcm->fd, SNDRV_PCM_IOCTL_INFO, &info)) {
         oops(pcm, errno, "cannot get info");
         goto fail_close;
@@ -884,7 +890,7 @@
     if (flags & PCM_NOIRQ) {
         if (!(flags & PCM_MMAP)) {
             oops(pcm, -EINVAL, "noirq only currently supported with mmap().");
-            goto fail;
+            goto fail_close;
         }
 
         params.flags |= SNDRV_PCM_HW_PARAMS_NO_PERIOD_WAKEUP;