public inbox for gcc-help@gcc.gnu.org
 help / color / mirror / Atom feed
From: Segher Boessenkool <segher@kernel.crashing.org>
To: Jim Wilson <jimw@sifive.com>
Cc: Fangrui Song <i@maskray.me>, gcc-help <gcc-help@gcc.gnu.org>
Subject: Re: Why does -g force .cfi_* directives?
Date: Sat, 20 Feb 2021 13:43:53 -0600	[thread overview]
Message-ID: <20210220194353.GT28121@gate.crashing.org> (raw)
In-Reply-To: <CAFyWVaZuB5RgT7nLB--qA8FeVjRGK-iJfB=-Obwj0HchCmpjaw@mail.gmail.com>

Hi!

On Fri, Feb 19, 2021 at 07:53:13PM -0800, Jim Wilson wrote:
> On Fri, Feb 19, 2021 at 4:36 PM Fangrui Song <i@maskray.me> wrote:
> > How should we make the following code work with both
> > -fno-asynchronous-unwind-tables and -fasynchronous-unwind-tables?
> >
> >    int main() {
> >      asm(".cfi_undefined %rip");
> >    }
> >
> 
> I don't think that there is a way currently to make this work.
> 
> In general, I'd say that if you are doing something non-trivial you should
> not be using an extended asm.  You should either use a built-in function or
> just write it in assembly language directly.  Extended asms really only
> work well for simple stuff.  If you use a built-in function, then the
> compiler should emit any CFI directives for that built-in if necessary. If
> writing in assembly language then you can hand write CFI directives for the
> entire function, or rely on assembler support if the assembler can figure
> it out from the code.

[ Well, I wouldn't say "non-trivial"...  But "more than a few machine
instructions", or "something that uses assembler pseudo-ops that aren't
set up for this (with push/pop for example), I certainly agree with it
if put that way. ]

An inline asm inserts a piece of text in the middle of the compiler
output.  You aren't even guaranteed it will be in *this* function, it
could be inlined, and could be cloned, etc.  Or deleted.

That can be dealt with by using a noipa attribute.  But then you get the
next problem:

You then know this asm will appear somewhere in the compiler output for
this function.  But where?  In this example there is likely no other
code generated for this function (if you have optimisation enabled!),
but for any useful function, you do not know.

(Btw, this is not an extended asm, this is a basic asm.  If you use at
least one colon it is en extended asm, and then you need to write
"%%rip", i.e., two percent signs).

> But if you really want to do this in an extended asm, then we would need to
> extend the asm syntax so that one can put CFI info in the middle of an
> asm.

But what would the semantics of that be?  You cannot control where in
the compiler output the asm will appear, or even if that is only once!
For example, in this code:

int a, b;
void f(int x)
{
	if (x)
		a++;
	else
		b++;
	asm("beacon");
}

the asm is output twice, since in effect the compiler makes this

int a, b;
void f(int x)
{
	if (x) {
		a++;
		asm("beacon");
		return;
	} else {
		b++;
		asm("beacon");
		return;
	}
}

> One way to do that might be a special operator for formatting asm
> strings that only prints the string if we are emitting unwind info.  We
> would have to find a free punctuation character that isn't already used by
> any existing port, and then assuming backquote is free we could do

There are no free characters this way: some code out there might output
backticks in its inline asm.  Everything not % (or {|} on some targets)
is emitted as-is (well, almost).

> int main() {
>      asm("`.cfi_undefined %rip`");
>    }
> and the backquotes then only print the string if we are emitting unwind
> info.  Or alternatively make this a % operator like %`.

Yes, that can work.  But you still have all the other problems with
abusing asm like this :-/

> Either way, I
> think this would look funny, so might not be the best approach.  It would
> likely be difficult for people to use.  I seriously doubt many users can
> write CFI code and get it right.

It often will depend on choices the compiler made, too, in which case 0
users can get it right!  They can get lucky, and sometimes it will do
what the user wanted.


Segher

  parent reply	other threads:[~2021-02-20 19:44 UTC|newest]

Thread overview: 9+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2021-02-18  5:21 Fangrui Song
2021-02-19 22:51 ` Jim Wilson
2021-02-20  0:36   ` Fangrui Song
2021-02-20  0:38     ` Fangrui Song
2021-02-20  3:53     ` Jim Wilson
2021-02-20  4:30       ` -fno-asynchronous-unwind-tables && .cfi_* in inline asm Fangrui Song
2021-02-22 19:08         ` Jim Wilson
2021-02-20 19:43       ` Segher Boessenkool [this message]
2021-02-26  7:09         ` Why does -g force .cfi_* directives? Fangrui Song

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20210220194353.GT28121@gate.crashing.org \
    --to=segher@kernel.crashing.org \
    --cc=gcc-help@gcc.gnu.org \
    --cc=i@maskray.me \
    --cc=jimw@sifive.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).