* RE: [PATCH bpf-next 08/13] uprobes/x86: Add support to optimize uprobes
[not found] ` <20241216101258.GA374@redhat.com>
@ 2024-12-16 11:10 ` David Laight
2024-12-16 12:22 ` Oleg Nesterov
0 siblings, 1 reply; 5+ messages in thread
From: David Laight @ 2024-12-16 11:10 UTC (permalink / raw)
To: 'Oleg Nesterov', linux-mm
Cc: 'Jiri Olsa',
Peter Zijlstra, Andrii Nakryiko, bpf, Song Liu, Yonghong Song,
John Fastabend, Hao Luo, Steven Rostedt, Masami Hiramatsu,
Alan Maguire, linux-kernel, linux-trace-kernel
From: Oleg Nesterov
> Sent: 16 December 2024 10:13
>
> David,
>
> let me say first that my understanding of this magic is very limited,
> please correct me.
I only (half) understand what the 'magic' has to accomplish and
some of the pitfalls.
I've copied linux-mm - someone there might know more.
> On 12/16, David Laight wrote:
> >
> > It all depends on how hard __replace_page() tries to be atomic.
> > The page has to change from one backed by the executable to a private
> > one backed by swap - otherwise you can't write to it.
>
> This is what uprobe_write_opcode() does,
And will be enough for single byte changes - they'll be picked up
at some point after the change.
> > But the problems arise when the instruction prefetch unit has read
> > part of the 5-byte instruction (it might even only read half a cache
> > line at a time).
> > I'm not sure how long the pipeline can sit in that state - but I
> > can do a memory read of a PCIe address that takes ~3000 clocks.
> > (And a misaligned AVX-512 read is probably eight 8-byte transfers.)
> >
> > So I think you need to force an interrupt while the PTE is invalid.
> > And that need to be simultaneous on all cpu running that process.
>
> __replace_page() does ptep_get_and_clear(old_pte) + flush_tlb_page().
>
> That's not enough?
I doubt it. As I understand it.
The hardware page tables will be shared by all the threads of a process.
So unless you hard synchronise all the cpu (and flush the TLB) while the
PTE is being changed there is always the possibility of a cpu picking up
the new PTE before the IPI that (I presume) flush_tlb_page() generates
is processed.
If that happens when the instruction you are patching is part-read into
the instruction decode buffer then you'll execute a mismatch of the two
instructions.
I can't remember the outcome of discussions about live-patching kernel
code - and I'm sure that was aligned 32bit writes.
>
> > Stopping the process using ptrace would do it.
>
> Not an option :/
Thought you'd say that.
David
>
> Oleg.
-
Registered Address Lakeside, Bramley Road, Mount Farm, Milton Keynes, MK1 1PT, UK
Registration No: 1397386 (Wales)
^ permalink raw reply [flat|nested] 5+ messages in thread
* Re: [PATCH bpf-next 08/13] uprobes/x86: Add support to optimize uprobes
2024-12-16 11:10 ` [PATCH bpf-next 08/13] uprobes/x86: Add support to optimize uprobes David Laight
@ 2024-12-16 12:22 ` Oleg Nesterov
2024-12-16 12:50 ` Jiri Olsa
0 siblings, 1 reply; 5+ messages in thread
From: Oleg Nesterov @ 2024-12-16 12:22 UTC (permalink / raw)
To: David Laight
Cc: linux-mm, 'Jiri Olsa',
Peter Zijlstra, Andrii Nakryiko, bpf, Song Liu, Yonghong Song,
John Fastabend, Hao Luo, Steven Rostedt, Masami Hiramatsu,
Alan Maguire, linux-kernel, linux-trace-kernel
OK, thanks, I am starting to share your concerns...
Oleg.
On 12/16, David Laight wrote:
>
> From: Oleg Nesterov
> > Sent: 16 December 2024 10:13
> >
> > David,
> >
> > let me say first that my understanding of this magic is very limited,
> > please correct me.
>
> I only (half) understand what the 'magic' has to accomplish and
> some of the pitfalls.
>
> I've copied linux-mm - someone there might know more.
>
> > On 12/16, David Laight wrote:
> > >
> > > It all depends on how hard __replace_page() tries to be atomic.
> > > The page has to change from one backed by the executable to a private
> > > one backed by swap - otherwise you can't write to it.
> >
> > This is what uprobe_write_opcode() does,
>
> And will be enough for single byte changes - they'll be picked up
> at some point after the change.
>
> > > But the problems arise when the instruction prefetch unit has read
> > > part of the 5-byte instruction (it might even only read half a cache
> > > line at a time).
> > > I'm not sure how long the pipeline can sit in that state - but I
> > > can do a memory read of a PCIe address that takes ~3000 clocks.
> > > (And a misaligned AVX-512 read is probably eight 8-byte transfers.)
> > >
> > > So I think you need to force an interrupt while the PTE is invalid.
> > > And that need to be simultaneous on all cpu running that process.
> >
> > __replace_page() does ptep_get_and_clear(old_pte) + flush_tlb_page().
> >
> > That's not enough?
>
> I doubt it. As I understand it.
> The hardware page tables will be shared by all the threads of a process.
> So unless you hard synchronise all the cpu (and flush the TLB) while the
> PTE is being changed there is always the possibility of a cpu picking up
> the new PTE before the IPI that (I presume) flush_tlb_page() generates
> is processed.
> If that happens when the instruction you are patching is part-read into
> the instruction decode buffer then you'll execute a mismatch of the two
> instructions.
>
> I can't remember the outcome of discussions about live-patching kernel
> code - and I'm sure that was aligned 32bit writes.
>
> >
> > > Stopping the process using ptrace would do it.
> >
> > Not an option :/
>
> Thought you'd say that.
>
> David
>
> >
> > Oleg.
>
> -
> Registered Address Lakeside, Bramley Road, Mount Farm, Milton Keynes, MK1 1PT, UK
> Registration No: 1397386 (Wales)
>
^ permalink raw reply [flat|nested] 5+ messages in thread
* Re: [PATCH bpf-next 08/13] uprobes/x86: Add support to optimize uprobes
2024-12-16 12:22 ` Oleg Nesterov
@ 2024-12-16 12:50 ` Jiri Olsa
2024-12-16 15:08 ` David Laight
0 siblings, 1 reply; 5+ messages in thread
From: Jiri Olsa @ 2024-12-16 12:50 UTC (permalink / raw)
To: Oleg Nesterov
Cc: David Laight, linux-mm, 'Jiri Olsa',
Peter Zijlstra, Andrii Nakryiko, bpf, Song Liu, Yonghong Song,
John Fastabend, Hao Luo, Steven Rostedt, Masami Hiramatsu,
Alan Maguire, linux-kernel, linux-trace-kernel
On Mon, Dec 16, 2024 at 01:22:05PM +0100, Oleg Nesterov wrote:
> OK, thanks, I am starting to share your concerns...
>
> Oleg.
>
> On 12/16, David Laight wrote:
> >
> > From: Oleg Nesterov
> > > Sent: 16 December 2024 10:13
> > >
> > > David,
> > >
> > > let me say first that my understanding of this magic is very limited,
> > > please correct me.
> >
> > I only (half) understand what the 'magic' has to accomplish and
> > some of the pitfalls.
> >
> > I've copied linux-mm - someone there might know more.
> >
> > > On 12/16, David Laight wrote:
> > > >
> > > > It all depends on how hard __replace_page() tries to be atomic.
> > > > The page has to change from one backed by the executable to a private
> > > > one backed by swap - otherwise you can't write to it.
> > >
> > > This is what uprobe_write_opcode() does,
> >
> > And will be enough for single byte changes - they'll be picked up
> > at some point after the change.
> >
> > > > But the problems arise when the instruction prefetch unit has read
> > > > part of the 5-byte instruction (it might even only read half a cache
> > > > line at a time).
> > > > I'm not sure how long the pipeline can sit in that state - but I
> > > > can do a memory read of a PCIe address that takes ~3000 clocks.
> > > > (And a misaligned AVX-512 read is probably eight 8-byte transfers.)
> > > >
> > > > So I think you need to force an interrupt while the PTE is invalid.
> > > > And that need to be simultaneous on all cpu running that process.
> > >
> > > __replace_page() does ptep_get_and_clear(old_pte) + flush_tlb_page().
> > >
> > > That's not enough?
> >
> > I doubt it. As I understand it.
> > The hardware page tables will be shared by all the threads of a process.
> > So unless you hard synchronise all the cpu (and flush the TLB) while the
> > PTE is being changed there is always the possibility of a cpu picking up
> > the new PTE before the IPI that (I presume) flush_tlb_page() generates
> > is processed.
> > If that happens when the instruction you are patching is part-read into
> > the instruction decode buffer then you'll execute a mismatch of the two
> > instructions.
if 5 byte update would be a problem, I guess we could workaround that through
partial updates using int3 like we do in text_poke_bp_batch?
- changing nop5 instruction to 'call xxx'
- write int3 to first byte of nop5 instruction
- have poke_int3_handler to emulate nop5 if int3 is triggered
- write rest of the call instruction to nop5 last 4 bytes
- overwrite first byte of nop5 with call opcode
similar update from 'call xxx' -> 'nop5'
thanks,
jirka
> >
> > I can't remember the outcome of discussions about live-patching kernel
> > code - and I'm sure that was aligned 32bit writes.
> >
> > >
> > > > Stopping the process using ptrace would do it.
> > >
> > > Not an option :/
> >
> > Thought you'd say that.
> >
> > David
> >
> > >
> > > Oleg.
> >
> > -
> > Registered Address Lakeside, Bramley Road, Mount Farm, Milton Keynes, MK1 1PT, UK
> > Registration No: 1397386 (Wales)
> >
>
^ permalink raw reply [flat|nested] 5+ messages in thread
* RE: [PATCH bpf-next 08/13] uprobes/x86: Add support to optimize uprobes
2024-12-16 12:50 ` Jiri Olsa
@ 2024-12-16 15:08 ` David Laight
2024-12-16 16:06 ` Jiri Olsa
0 siblings, 1 reply; 5+ messages in thread
From: David Laight @ 2024-12-16 15:08 UTC (permalink / raw)
To: 'Jiri Olsa', Oleg Nesterov
Cc: linux-mm, Peter Zijlstra, Andrii Nakryiko, bpf, Song Liu,
Yonghong Song, John Fastabend, Hao Luo, Steven Rostedt,
Masami Hiramatsu, Alan Maguire, linux-kernel, linux-trace-kernel
From: Jiri Olsa
> Sent: 16 December 2024 12:50
>
> On Mon, Dec 16, 2024 at 01:22:05PM +0100, Oleg Nesterov wrote:
> > OK, thanks, I am starting to share your concerns...
> >
> > Oleg.
> >
> > On 12/16, David Laight wrote:
> > >
> > > From: Oleg Nesterov
> > > > Sent: 16 December 2024 10:13
> > > >
> > > > David,
> > > >
> > > > let me say first that my understanding of this magic is very limited,
> > > > please correct me.
> > >
> > > I only (half) understand what the 'magic' has to accomplish and
> > > some of the pitfalls.
> > >
> > > I've copied linux-mm - someone there might know more.
> > >
> > > > On 12/16, David Laight wrote:
> > > > >
> > > > > It all depends on how hard __replace_page() tries to be atomic.
> > > > > The page has to change from one backed by the executable to a private
> > > > > one backed by swap - otherwise you can't write to it.
> > > >
> > > > This is what uprobe_write_opcode() does,
> > >
> > > And will be enough for single byte changes - they'll be picked up
> > > at some point after the change.
> > >
> > > > > But the problems arise when the instruction prefetch unit has read
> > > > > part of the 5-byte instruction (it might even only read half a cache
> > > > > line at a time).
> > > > > I'm not sure how long the pipeline can sit in that state - but I
> > > > > can do a memory read of a PCIe address that takes ~3000 clocks.
> > > > > (And a misaligned AVX-512 read is probably eight 8-byte transfers.)
> > > > >
> > > > > So I think you need to force an interrupt while the PTE is invalid.
> > > > > And that need to be simultaneous on all cpu running that process.
> > > >
> > > > __replace_page() does ptep_get_and_clear(old_pte) + flush_tlb_page().
> > > >
> > > > That's not enough?
> > >
> > > I doubt it. As I understand it.
> > > The hardware page tables will be shared by all the threads of a process.
> > > So unless you hard synchronise all the cpu (and flush the TLB) while the
> > > PTE is being changed there is always the possibility of a cpu picking up
> > > the new PTE before the IPI that (I presume) flush_tlb_page() generates
> > > is processed.
> > > If that happens when the instruction you are patching is part-read into
> > > the instruction decode buffer then you'll execute a mismatch of the two
> > > instructions.
>
> if 5 byte update would be a problem, I guess we could workaround that through
> partial updates using int3 like we do in text_poke_bp_batch?
>
> - changing nop5 instruction to 'call xxx'
> - write int3 to first byte of nop5 instruction
> - have poke_int3_handler to emulate nop5 if int3 is triggered
> - write rest of the call instruction to nop5 last 4 bytes
> - overwrite first byte of nop5 with call opcode
That might work provided there are IPI (to flush the decode pipeline)
after the write of the 'int3' and one before the write of the 'call'.
You'll need to ensure the I-cache gets invalidated as well.
And if the sequence crosses a page boundary....
David
>
> similar update from 'call xxx' -> 'nop5'
>
> thanks,
> jirka
>
> > >
> > > I can't remember the outcome of discussions about live-patching kernel
> > > code - and I'm sure that was aligned 32bit writes.
> > >
> > > >
> > > > > Stopping the process using ptrace would do it.
> > > >
> > > > Not an option :/
> > >
> > > Thought you'd say that.
> > >
> > > David
> > >
> > > >
> > > > Oleg.
> > >
> > > -
> > > Registered Address Lakeside, Bramley Road, Mount Farm, Milton Keynes, MK1 1PT, UK
> > > Registration No: 1397386 (Wales)
> > >
> >
-
Registered Address Lakeside, Bramley Road, Mount Farm, Milton Keynes, MK1 1PT, UK
Registration No: 1397386 (Wales)
^ permalink raw reply [flat|nested] 5+ messages in thread
* Re: [PATCH bpf-next 08/13] uprobes/x86: Add support to optimize uprobes
2024-12-16 15:08 ` David Laight
@ 2024-12-16 16:06 ` Jiri Olsa
0 siblings, 0 replies; 5+ messages in thread
From: Jiri Olsa @ 2024-12-16 16:06 UTC (permalink / raw)
To: David Laight
Cc: 'Jiri Olsa',
Oleg Nesterov, linux-mm, Peter Zijlstra, Andrii Nakryiko, bpf,
Song Liu, Yonghong Song, John Fastabend, Hao Luo, Steven Rostedt,
Masami Hiramatsu, Alan Maguire, linux-kernel, linux-trace-kernel
On Mon, Dec 16, 2024 at 03:08:14PM +0000, David Laight wrote:
> From: Jiri Olsa
> > Sent: 16 December 2024 12:50
> >
> > On Mon, Dec 16, 2024 at 01:22:05PM +0100, Oleg Nesterov wrote:
> > > OK, thanks, I am starting to share your concerns...
> > >
> > > Oleg.
> > >
> > > On 12/16, David Laight wrote:
> > > >
> > > > From: Oleg Nesterov
> > > > > Sent: 16 December 2024 10:13
> > > > >
> > > > > David,
> > > > >
> > > > > let me say first that my understanding of this magic is very limited,
> > > > > please correct me.
> > > >
> > > > I only (half) understand what the 'magic' has to accomplish and
> > > > some of the pitfalls.
> > > >
> > > > I've copied linux-mm - someone there might know more.
> > > >
> > > > > On 12/16, David Laight wrote:
> > > > > >
> > > > > > It all depends on how hard __replace_page() tries to be atomic.
> > > > > > The page has to change from one backed by the executable to a private
> > > > > > one backed by swap - otherwise you can't write to it.
> > > > >
> > > > > This is what uprobe_write_opcode() does,
> > > >
> > > > And will be enough for single byte changes - they'll be picked up
> > > > at some point after the change.
> > > >
> > > > > > But the problems arise when the instruction prefetch unit has read
> > > > > > part of the 5-byte instruction (it might even only read half a cache
> > > > > > line at a time).
> > > > > > I'm not sure how long the pipeline can sit in that state - but I
> > > > > > can do a memory read of a PCIe address that takes ~3000 clocks.
> > > > > > (And a misaligned AVX-512 read is probably eight 8-byte transfers.)
> > > > > >
> > > > > > So I think you need to force an interrupt while the PTE is invalid.
> > > > > > And that need to be simultaneous on all cpu running that process.
> > > > >
> > > > > __replace_page() does ptep_get_and_clear(old_pte) + flush_tlb_page().
> > > > >
> > > > > That's not enough?
> > > >
> > > > I doubt it. As I understand it.
> > > > The hardware page tables will be shared by all the threads of a process.
> > > > So unless you hard synchronise all the cpu (and flush the TLB) while the
> > > > PTE is being changed there is always the possibility of a cpu picking up
> > > > the new PTE before the IPI that (I presume) flush_tlb_page() generates
> > > > is processed.
> > > > If that happens when the instruction you are patching is part-read into
> > > > the instruction decode buffer then you'll execute a mismatch of the two
> > > > instructions.
> >
> > if 5 byte update would be a problem, I guess we could workaround that through
> > partial updates using int3 like we do in text_poke_bp_batch?
> >
> > - changing nop5 instruction to 'call xxx'
> > - write int3 to first byte of nop5 instruction
> > - have poke_int3_handler to emulate nop5 if int3 is triggered
> > - write rest of the call instruction to nop5 last 4 bytes
> > - overwrite first byte of nop5 with call opcode
>
> That might work provided there are IPI (to flush the decode pipeline)
> after the write of the 'int3' and one before the write of the 'call'.
> You'll need to ensure the I-cache gets invalidated as well.
ok, seems to be done by text_poke_sync
>
> And if the sequence crosses a page boundary....
that was already limitation for the current change
jirka
^ permalink raw reply [flat|nested] 5+ messages in thread
end of thread, other threads:[~2024-12-16 16:06 UTC | newest]
Thread overview: 5+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
[not found] <20241211133403.208920-1-jolsa@kernel.org>
[not found] ` <20241211133403.208920-9-jolsa@kernel.org>
[not found] ` <1521ff93bc0649b0aade9cfc444929ca@AcuMS.aculab.com>
[not found] ` <20241215141412.GA13580@redhat.com>
[not found] ` <Z1_gFymfO3sAwhiY@krava>
[not found] ` <c5fb22629d3f42798def5b63ce834801@AcuMS.aculab.com>
[not found] ` <20241216101258.GA374@redhat.com>
2024-12-16 11:10 ` [PATCH bpf-next 08/13] uprobes/x86: Add support to optimize uprobes David Laight
2024-12-16 12:22 ` Oleg Nesterov
2024-12-16 12:50 ` Jiri Olsa
2024-12-16 15:08 ` David Laight
2024-12-16 16:06 ` Jiri Olsa
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox