[Lldb-commits] [PATCH] Skip symlinks to the original file when searching for debug info
Zachary Turner
zturner at google.com
Mon Feb 23 14:09:00 PST 2015
I agree that for the reasons you point out, writing a low level llvm API
call is not the right approach. But a FileSystem class seems like a great
place for this. A platform is not necessary to append a path component or
normalize a path, for example. So why muddy up its implementation with
things that not everything cares about? Would you require every FileSpec
to be created with a platform? Or only support using the currently
selected platform for operations? Or would you have the operations take a
platform as one of their arguments? None of the options is particularly
appealing to me.
So instead, why not this:
FileSpec spec1("/Foo/Project/subdirA/../headers/foo.h");
FileSpec spec2("/Foo/Project/subdirB/../headers/foo.h");
FileSystem FS(platform_sp);
if (FS.equivalent(spec1, spec2)) {
}
On Mon Feb 23 2015 at 2:03:31 PM <jingham at apple.com> wrote:
>
> > On Feb 23, 2015, at 1:51 PM, Zachary Turner <zturner at google.com> wrote:
> >
> > Well I really like to keep ifdefs out of code. I know that Host is the
> place for ifdefs, and FileSpec is in Host, but I still like to keep them to
> a minimum. It's too easy to break things when you have to try to figure
> out which ifdef paths you need to modify. That was the reason for creating
> the FileSystem class. It exposes a platform agnostic interface to low
> level FS operations. Similar to llvm::sys::fs, and there's probably some
> duplication there that could be removed, but I just didn't want to break
> too much stuff at the time.
>
> >
> > I really wouldn't want to see a bunch of ifdefs ending up in FileSpec
> (there's already some there that I'd like to see removed, as described
> below). A lot of what it does is consistent across all platforms and is
> just focused on splitting apart a string, and constifying the directory and
> filename portions. And so I think it would be a shame to muck up this
> (mostly) platform-agnostic class with some platform specific stuff. It
> would be great if there were a way to isolate the disk access part. I
> don't think it's too crazy to write something like
> >
> > FileSpec MyFile("/usr/bin/foo");
> > FileSystem::DirectoryEnumerator Enumerator(MyFile);
> > for (FileSpec &Child : Enumerator) {
> > if (FileSystem::IsDirectory(Child)) {
> > // Do something.
> > }
> > }
> >
> > In fact I think it's even better.
> > 1) It improves readability by making it clear that you're hitting the
> file system, so you should be careful about what type of path you're using.
> > 2) It improves modularity by isolating the code that hits the file
> system from the code that doesn't.
> > 3) It cleans up the FileSpec implementation somewhat. Currently
> EnumerateDirectory is a big ugly function with a couple of different
> preprocessor branches.
> > 4) Separating the responsibilities like this leads to more flexible
> usage patterns. Like having DirectoryEnumerator be an object that can be
> used in a range-based for loop here, instead of forcing its usage to
> conform to what you can write with a single function call.
>
> > Anyway, TL;DR of all this is that I know it was originally designed to
> be all things related to files, but as it grows, it starts to become really
> heavy. I think it makes sense to consider a separation of
> responsibilities. Does a function that mmaps file contents really belong
> in the same class as a function that resolves a symlink? I don't think we
> need or even should have 1 class that is all things file system. We should
> try to find ways to break it down into smaller, more targeted, more
> meaningful components.
> >
>
> I don't think I agree with this. For instance, when clang writes the
> dependent file records in debug information it writes them relative to the
> current compilation directory, so for complex compiles, on Unix you can end
> up with one source file that contains paths like:
>
> /Foo/Project/subdirA/../headers/foo.h
>
> and another:
>
> /Foo/Project/subdirB/../headers/foo.h
>
> If you want to do equivalence of these two headers (e.g. if somebody sets
> a breakpoint by full name) then I want to know "on the target platform, can
> these two files be the same file." It's weird that I can't ask the file
> spec I was handed this question, it will give me an answer, but probably a
> wrong one. Instead I have to pass the paths to some FileSystem call or
> even weirder some lower level llvm call that knows nothing about these
> files, and for sure is going to fail if they are remote... The FileSpec
> has a chance to be able to answer this cause it was around from the time
> the reference was created and we can add info as needed to make this
> possible. But watering it down to a string and then trying to recover
> extra information later on seems very error-prone. And having to know
> which actor to ask this sort of question also seems error-prone.
>
> Jim
>
>
> > On Mon Feb 23 2015 at 1:23:54 PM <jingham at apple.com> wrote:
> >
> > > On Feb 23, 2015, at 1:17 PM, Zachary Turner <zturner at google.com>
> wrote:
> > >
> > > In http://reviews.llvm.org/D7836#128511, @jingham wrote:
> > >
> > >> That is not how we thought of FileSpec originally. It clearly was
> meant to deal with real files (for instance it has Exists methods & Read,
> etc.) It was meant to be a wrapper that would allow us to do all the
> useful file manipulation in a system-independent way. It ended up with
> system dependencies just because we didn't have the time to keep it clean
> when there were no ports of lldb that weren't Unix... But that's life, not
> design.
> > >>
> > >> Anyway, it would be weird to have some object you use to denote the
> files you are interested in, but then when you actually want to do
> something with them, you have to turn around and use another object. And
> it would be unfortunate to have to write system specific code at this point
> except for the - hopefully very few - cases where the sort of thing we want
> to do to a file is not able to be expressed in a system-independent way.
> > >>
> > >> Jim
> > >
> > >
> > > Well, already we have introduced the notion of the path syntax so that
> FileSpec can in theory refer to a path that is invalid for the host you're
> on. In that case it doesn't make much sense to have a Windows path, for
> example on Mac, and then try to do a file system operation on it. When I
> refactored some of Host months ago, there were other methods directly in
> Host that would do things like get file permissions, etc. So there was
> already some separation between the FileSpec and the methods that hit the
> file system. Most of that stuff ended up in FileSystem, and the stuff that
> remains in FileSpec is only there because I couldn't change the public API.
> > >
> > > But with the notion of a FileSpec that can refer to a path that can't
> possibly be on your local host, I think it makes sense to consider whether
> the file system access routines should be separated from FileSpec.
> >
> > Not sure, wouldn't it be better to optionally attach a platform to
> FileSpec, so that FileSpecs can transparently handle remote access?
> FileSpec's are how we specify files. Seems awkward to switch gears to
> something else when you actually want to access them.
> >
> > Jim
> >
> >
> > >
> > >
> > > http://reviews.llvm.org/D7836
> > >
> > > EMAIL PREFERENCES
> > > http://reviews.llvm.org/settings/panel/emailpreferences/
> > >
> > >
> >
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/lldb-commits/attachments/20150223/fce53ba0/attachment.html>
More information about the lldb-commits
mailing list