There's nothing that says that your daemons have to be MPI processes. They could be proper system-level daemons that live "forever", for example. You might not be able to speak to them via MPI easily (e.g., you may need to use TCP sockets or some other network transport), but this is fairly common client/server stuff.
Or you could use MPI_COMM_CONNECT / MPI_COMM_ACCEPT to connect to them, if they're long-lived MPI jobs. That gets a bit more complicated; I'm not sure how well we've tested having a "server"-like MPI process around with repeated connects/disconnects for long periods of time. The failure model may also not be attractive (i.e., if your MPI job MPI connects to the server, but then segv's -- it might likely take down the server, too).
That being said, any additional monitoring or querying of what to do will add overhead. Hence, your techniques might be useful for large IO operations, for example. Or every Nth small operation. It's just a question of balancing the overhead of the query/reply with the expected duration of the IO operation(s) that you intend to perform. I suspect that you can probably model this overhead and then refine it with some empirical data. I suspect that you can supplement such a query scheme with some level of caching on the rationale that if an app does IO pattern X once, it might need to do it multiple times. So if you query for it once, you can just keep that result around for a little while in case the same pattern comes up again -- you won't necessarily need to query for it again.
The tricky part is that everyone's HPC setup is different -- the exact/empirical overhead of the query/reply will likely be highly tied to a user's particular hardware, software stack, network setup, back-end filesystem, etc.
One more thing -- to expand on what Ralph said, there's two kinds of typical MPI IO optimizations that are possible:
1. one-time optimizations during startup: this is usually effected via OMPI's MCA parameters, and is only performed when OMPI's MPI IO subsystem is initialized. This is typically the first time an app calls MPI_FILE_OPEN.
2. MPI_Info hints that are passed in to each MPI IO operation. These obviously are much more flexible and timely (since they can be passed in to each operation, and/or to MPI_FILE_OPEN).
On Jun 13, 2012, at 10:32 AM, Xuan Wang wrote:
> Hi Ralph,
> you are right, the monitor hurts the performance, if the monitor has to sent the monitoring results to the data warehouse during the execution of the I/O operation. But actually, we don't need this parallel execution for the monitor. The monitor only need to gather the information such as the duration of read/write, the bandwidth, the number of used processes, the algorithm ID and some other small information. This information can be stored as txt file and sent to the data warehouse when the file system is free, which means the monitor sends information to the data warehouse "OFFLINE".
You might find that IO -- particularly parallel IO -- is a *highly* complex issue with many different variables involved. Specifically: it may be better to save as much meta data as possible, not just number of bytes and number of processes (for example). Position in the file may also be relevant (e.g., you may be able to infer the file systems caching algorithms from information like this, which will have a significant effect on overall performance). And so on.
> I will try to find out the impact of comm_spawn to the whole performance. Besides starting another MPI process to monitoring the performance, is there any possibility to integrating a monitoring function within the MPI process or even within the MPI I/O operation? That means we start one MPI process, there are multiple threads for I/O operations, in which one thread is in charge of monitoring. Will that hurt a lot of performance? If necessary, the Open MPI source code has to be overwritten for this purpose.
Sure, you can do this. If you spawn off multiple threads, if they block most of the time (and I really mean *most* of the time), that's no big deal. Or you could interpose your IO module with some other back-end module (like ROMIO or OMPIO), and thereby intercept all MPI IO calls to see the parameters going by, possibly even having visibility on when those operations complete (but this might get a little tricky for request-based non-blocking IO -- you'd have to interpose your own request to know when the real request has completed... hmm... that could get tricky... I'm not even sure it could be done in the current code base; I'd have to think about it...).
> The database is actually independent to the I/O operation. The only disadvantage I can see, is that the MPI process has to wait for accessing the database. Especially the table in very large.
If your query thread to the database is off in a thread, the IO operation could always wait for a short period of time for the answer, and if it doesn't get it, give up and let the database query proceed in the background (e.g., might as well let it complete and cache the result in case you do the same IO operation in the future) while you let the IO operation proceed in the foreground (so to speak).
> The goal of this concept is to automatically adjust the I/O operation parameters according to the historical I/O operation results, so that each I/O operation will execute at least not worse than last similar I/O operations. Therefore the system includes a learning phase - the better combination of the parameters and algorithm replaces the older and worse one.
Sure. That's a good goal.
But keep in mind that past performance is not always a good indicator of future performance. For example, the filesystem may perform very differently for the same operation at times X, Y, and Z. What if the filesystem was empty at time X, but 99.99999% full at time Y? What if the network fileserver was busy with other requests at time Z? All of these things can dramatically impact the delivered performance, and not all of these factors are easily directly observable by you.
My *guess* is that past behavior of large, coarse-grained operations might well be suitable for future performance predictions (e.g., if you're going to a 20MB shared write, use hints A, B, and C). But small, fine-grained application hints may be too transient and sensitive to external factors to be reliably based on past performance. (that's a *guess* -- feel free to prove me wrong! :-) )
My real point is -- and I know that I'm repeating myself :-) -- storage/IO is very, very complex. There are multiple opaque levels of hardware and software involved. Here's a few:
- the MPI layer
- the OS filesystem
- the network (if it's a network filesystem, or is otherwise talking to one or more remote servers, such as with parallel filesystems)
- the storage controller (some of which have multiple levels of caching and/or aggregation)
- the back-end disks themselves
...and there could even be more. Some storage controllers, for example, offer front-end SSD caches to back-end HDD's these days. Yow. I don't even know how to begin to profile the performance of such systems under complicated load patterns.
Hope this helps!
For corporate legal information go to: http://www.cisco.com/web/about/doing_business/legal/cri/