Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Crash in blocking_multi_transfer() ? #38

Closed
jcharaoui opened this issue Jul 21, 2019 · 8 comments
Closed

Crash in blocking_multi_transfer() ? #38

jcharaoui opened this issue Jul 21, 2019 · 8 comments

Comments

@jcharaoui
Copy link
Collaborator

jcharaoui commented Jul 21, 2019

I hit this when testing, cache mode off, and caused HTTPDirFS to crash:

blocking_multi_transfer(): 8, API function called from within callback

I haven't been able to reproduce it so far, but it may be indicative of a problem.

@fangfufu
Copy link
Owner

It appears that I copied at pasted blocking_multi_transfer() to multiple places. I pushed a commit with updated error messages. Please recompile to see if this can be reproduced again.

@fangfufu
Copy link
Owner

By the way, what are you doing to discover so many bugs? Do you reckon we should start writing test harnesses?

@jcharaoui
Copy link
Collaborator Author

One of the uses I have for HTTPDirFS is streaming video, eg. reading large (>250 MB) video files with mplayer or VLC. While non-cached mode still seems to work well as in 1.0.1, with cached mode it's not as stable. The video player will keep requesting data to fill its own application cache, causing HTTPDirFS to gradually download data into its own cache, but sometimes it stops and hangs, and I have to kill -9 it.

Testing really wouldn't hurt in my opinion, but in terms of writing actual tests for a C program like this, that's beyond my level of expertise.

@fangfufu
Copy link
Owner

sometimes it stops and hangs, and I have to kill -9 it

Sounds like deadlock to me, I am not that surprised, considering how many mutexes I have to put into the cache related codes. I didn't do well in concurrency programming when I was an undergraduate...

One of the uses I have for HTTPDirFS is streaming video

Actually one of the primary way for me to test the program was to play video files. A lot of work was put into prefetching the next download segment. Anyway, it would be nice if you link me to the server that's causing you problem, and let me play those video files. You could just put up some dummy video files.

The video player will keep requesting data to fill its own application cache, causing HTTPDirFS to gradually download data into its own cache, but sometimes it stops and hangs, and I have to kill -9 it.

I don't promise I can reproduce the exact bug, because deadlocks only show up when certain sequence of events show up, but I am happy to give it a go.

By the way my base64 encoded email address is ZmFuZ2Z1ZnUyMDAzQGdtYWlsLmNvbQo=, if you want to send me the link to the server / video file in question.

@fangfufu
Copy link
Owner

fangfufu commented Jul 22, 2019

I just watched a film on my own server, it worked fine. So I guess I might need your particular server to figure out what's going on.

@fangfufu
Copy link
Owner

Please try compiling and running the latest commit, and post the log file when it deadlocks. This version produces more debug messages associated with locks, and I modified locking sequence.

@fangfufu
Copy link
Owner

@jcharaoui , here is an update on the situation,

So libfuse issues concurrent read threads. This is how HTTPDirFS process them:

  • When HTTPDirFS operates in non-cached mode, these read threads get directly translated to HTTP requests.
  • When it operates in cached mode, these concurrent read threads get serialised. This is to avoid multiple writes to the cache.

So far I can't see any deadlocks in cached mode. However if somehow the HTTP connection hangs during when you are using the cache mode, you have to wait for libcurl to timeout before another read request gets accepted. Whereas in non-cache mode, HTTPDirFS would immediate honour another read request. Quite often libfuse requests two consecutive 128KB blocks in two separate threads. In cached mode, the second request gets blocked until the 8MB segment is fully downloaded.

@fangfufu
Copy link
Owner

same bug got reported in issue #40

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants