Laszlo,

Good feedback.  As I mentioned earlier, we are cleaning up these modules.  We
can make sure everything is consistent for the "borrow" case.

I agree it would be better to "borrow" a page that is not being used by
any other PEIM.  We will consider ASSERT() if there is no free memory.

Mike

> -----Original Message-----
> From: Laszlo Ersek [mailto:[email protected]]
> Sent: Thursday, July 7, 2016 10:49 AM
> To: Kinney, Michael D <[email protected]>; Fan, Jeff 
> <[email protected]>;
> Justen, Jordan L <[email protected]>
> Cc: Paolo Bonzini <[email protected]>; edk2-devel-01 
> <[email protected]>
> Subject: Re: [edk2] multiprocessing in PEI?
> 
> On 07/07/16 19:33, Kinney, Michael D wrote:
> > Laszlo,
> >
> > If all memory below 640K is allocated for use by other PEIMs, the "borrow" 
> > technique
> can still work
> > for the CpuMpPeim.
> >
> > If we add the scanning code for 2B, we will just ignore the result anyways 
> > if all
> memory below
> > 640K is already allocated.
> 
> I think I disagree. In that case CpuMpPei should ASSERT() and then call
> CpuDeadLoop() explicitly.
> 
> Minimally, some kind of arbitration is necessary between CpuMpPei and
> another PEIM that performs the same kind of borrowing. If both of these
> PEIMs go ahead and just ignore the results anyways, that could be very bad.
> 
> Either way, the fact that CpuMpPei produces a memalloc HOB at the end,
> for the buffer that it borrows, is just inconsistent with the fact that
> CpuMpPei does not consider memalloc HOBs that other PEIMs have produced
> earlier.
> 
> > So we will add logic with no value.  I think there are two different
> > cases here.  One for permanent allocation of memory by a PEIM, and another 
> > is
> "borrow" for a
> > short period of time with no chance for confict.
> 
> If it's only for a short period of time, with no chance for conflict,
> then what justifies the BuildMemoryAllocationHob() call when
> GetWakeupBuffer() is about to return with success?
> 
> Actually, I think there's a pretty large chance for conflict here. The
> borrowed area is retained by CpuMpPei until End-of-PEI. At End-of-PEI,
> the area is either simply released (normal boot path) or restored (S3
> resume path). The CpuMpEndOfPeiCallback() function is called by the PEI
> Core way after CpuMpPeimInit() returns -- an arbitrary number of other
> PEIMs can be dispatched in the meantime, at least one of which could
> perform a similar scan.
> 
> So, I actually agree with the BuildMemoryAllocationHob() call in
> GetWakeupBuffer(). I disagree with "no chance for conflict", and for
> that reason I think GetWakeupBuffer() should consider preexistent
> memalloc HOBs too.
> 
> > You raise good points to make sure we provide
> > great examples for other PEIMs to follow.  In this case, I would recommend 
> > a detailed
> comment
> > block that describes the "borrow" technique and why the memory allocation 
> > HOBs are
> not scanned
> > in this specific case.
> 
> I'd be really pleased with that, but only if it proves my above argument
> wrong :)
> 
> Thanks!
> Laszlo
> 
> >> -----Original Message-----
> >> From: Laszlo Ersek [mailto:[email protected]]
> >> Sent: Thursday, July 7, 2016 2:15 AM
> >> To: Fan, Jeff <[email protected]>; Kinney, Michael D 
> >> <[email protected]>;
> >> Justen, Jordan L <[email protected]>
> >> Cc: Paolo Bonzini <[email protected]>; edk2-devel-01 
> >> <[email protected]>
> >> Subject: Re: [edk2] multiprocessing in PEI?
> >>
> >> On 07/07/16 10:56, Fan, Jeff wrote:
> >>> Laszlo,
> >>>
> >>> Any PEI module cannot allocate the memory < 1MB range if using PEI memory
> allocation
> >> services only.
> >>
> >> Okay.
> >>
> >>> If other PEI module wants to allocate the memory by scanning memory 
> >>> resource HOB,
> it
> >> has to follow the same rule with the CpuMpPei driver.
> >>
> >> Okay.
> >>
> >>> If platform build allocation HOB for the whole range < 1MB,  how to avoid 
> >>> memory
> >> conflicts between CpuMpPei and other PEI modules who is scanning memory 
> >> resource
> HOB?
> >>
> >> You are right about this, in theory.
> >>
> >> Your suggestion is that any PEIM that needs memory under 1MB look for
> >> memory HOBs, and stay away from memory allocation HOBs. In other words,
> >> to build a map from memory HOBs, subtract the memory allocation HOBs,
> >> grab a chunk from what remains, and then cover that chunk with another
> >> allocation HOB. This will ensure complete understanding between the
> >> platfom PEIM, CpuMpPei, and any other PEIMs.
> >>
> >> I agree completely, except for the fact that in practice, CpuMpPei
> >> currently *ignores* any memory allocation HOBs!
> >>
> >> CpuMpPei creates a memalloc HOB for the chunk that it ultimately
> >> borrows, yes -- but how can CpuMpPei expect other PEIMs to honor its
> >> memalloc HOB when CpuMpPei ignores memalloc HOBs from other PEIMs?
> >>
> >> In other words, I can agree that OVMF's Platform PEIM should not create
> >> a memalloc HOB (only the memory HOB) for 0..640KB, but *only if*
> >> CpuMpPei is patched to honor preexistent memalloc HOBs in 
> >> GetWakeupBuffer().
> >>
> >> Then we can say we have a pattern that all PEIMs are expected to follow:
> >>
> >> (1) memory can be allocated for any use with the PEI services
> >>
> >> (2) memory can be allocated under 1MB by
> >>     (2a) looking for memory HOBs
> >>     (2b) *and* honoring existing memalloc HOBs.
> >>
> >>     (2c) The memory taken this way should be covered by the consumer
> >>          with another memalloc HOB.
> >>     (2d) Also, if allocation occurs on the S3 resume path, then the
> >>          original contents must be restored at End-of-PEI.
> >>
> >> This method is safe for all PEIMs to follow, but CpuMpPei itself does
> >> not comply with it (step (2b)).
> >>
> >> Thanks
> >> Laszlo
> >>
> >>
> >>>
> >>> Jeff
> >>>
> >>> -----Original Message-----
> >>> From: Laszlo Ersek [mailto:[email protected]]
> >>> Sent: Thursday, July 07, 2016 4:48 PM
> >>> To: Fan, Jeff; Kinney, Michael D; Justen, Jordan L
> >>> Cc: Paolo Bonzini; edk2-devel-01
> >>> Subject: Re: [edk2] multiprocessing in PEI?
> >>>
> >>> On 07/07/16 10:29, Fan, Jeff wrote:
> >>>> Laszlo,
> >>>>
> >>>> Actually, CpuMpPei has no knowledge to know which memory range < 1MB is 
> >>>> available
> or
> >> not. That's why we cannot assume one hardcode address < 1MB for borrowing.
> >>>
> >>> I agree that this makes sense.
> >>>
> >>>>
> >>>> Platform has such knowledge and need one mechanism to tell CpuMpPei.
> >>>
> >>> I agree 100%.
> >>>
> >>>> We choose Memory Resource HOB here.
> >>>
> >>> I believe this is not a perfect choice.
> >>>
> >>> The information that the memory resource HOB conveys can be unwittingly 
> >>> mis-used by
> >> other PEIMs. The information from the platform is good, but it is not 
> >> targeted /
> >> restricted well enough.
> >>>
> >>> As I wrote in my other email, the restriction should be
> >>>
> >>>   available for temporary use, but only if the original contents are
> >>>   restored at End-of-PEI.
> >>>
> >>> CpuMpPei certainly complies with this restriction, but other PEIMs won't 
> >>> realize it
> >> just from looking at a memory resource HOB.
> >>>
> >>> So, as a workaround, I have to install a memory allocation HOB as well, 
> >>> in OVMF's
> >> Platform PEIM. CpuMpPei will ignore the memalloc HOB (and take care to 
> >> restore the
> >> borrowed area at End-of-PEI). And any other PEIMs should steer clear of 
> >> the area
> >> because of the memalloc HOB.
> >>>
> >>> Thanks
> >>> Laszlo
> >>>
> >>>>
> >>>> Thanks!
> >>>> Jeff
> >>>>
> >>>> -----Original Message-----
> >>>> From: Laszlo Ersek [mailto:[email protected]]
> >>>> Sent: Thursday, July 07, 2016 3:04 PM
> >>>> To: Fan, Jeff; Kinney, Michael D; Justen, Jordan L
> >>>> Cc: Paolo Bonzini; edk2-devel-01
> >>>> Subject: Re: [edk2] multiprocessing in PEI?
> >>>>
> >>>> On 07/07/16 04:52, Fan, Jeff wrote:
> >>>>> Laszlo,
> >>>>>
> >>>>> On PEI phase, whatever  it is normal boot or S3 boot, PEI memory 
> >>>>> allocation
> >> services should not allocate memory < 1 MB address.
> >>>>>
> >>>>> If any other PEIM module wants to allocate memory < 1 MB address, it 
> >>>>> has to scan
> >> Memory resource HOB to find the available memory range and build memory 
> >> allocation
> HOB
> >> like what CpuMpPei did.
> >>>>>
> >>>>> If this method is OK, CpuMpPei or other module are required to check 
> >>>>> existing
> both
> >> memory resource HOB and memory allocation HOB.
> >>>>>
> >>>>> If we just borrow one piece of range < 1 MB address around each of 
> >>>>> INIT-SIPI-SIPI
> >> to AP, we still need to get the available memory address.
> >>>>>
> >>>>> So, platform still needs to build memory resource HOB < 1MB on S3 boot 
> >>>>> like
> normal
> >> boot.  I think this update on platform  should be simpler than new pair of 
> >> PCDs
> >> introducing.
> >>>>>
> >>>>> What do you think of it?
> >>>>
> >>>> * First, at this point I'm now thinking that "borrowing" and 
> >>>> "allocating" are
> >> actually separate things:
> >>>>
> >>>> (a) For allocating memory under 1MB, scanning both the memory resource
> >>>>     HOBs and the memory allocation HOBs would be necessary, yes.
> >>>>
> >>>> (b) However, in case the memory under 1MB is only borrowed (and the
> >>>>     backup buffer is allocated with the PEI serivces), the HOB scanning
> >>>>     should not be necessary at all (for any kinds of HOBs). CpuMpPei
> >>>>     is intimately tied to Intel real mode anyway (hence the < 1MB
> >>>>     requirement in the first place), so why can't CpuMpPei just borrow
> >>>>     a few pages at a fixed low address (under 640KB)? That memory is
> >>>>     required to exist on platforms where CpuMpPei is supposed to run,
> >>>>     isn't it?
> >>>>
> >>>> * Second, the reason I'm reluctant to produce the same set of memory 
> >>>> resource and
> >> alloc HOBs  on the S3 resume path as on the normal boot path is the 
> >> following:
> >>>>
> >>>> In my opinion, that would be misleading. Other PEIMs that execute (a) -- 
> >>>> that is,
> >> allocation and not borrowing -- might think that any memory that is 
> >> covered by a
> >> resource descriptor HOB, but not covered by any allocation HOBs, is "free 
> >> memory".
> >> While in fact that memory could well be used by the OS.
> >>>>
> >>>> In other words, the reason why we don't produce any of these HOBs is 
> >>>> exactly to
> >> communicate that there is zero free memory *for allocation*, outside of 
> >> the PEI
> memory
> >> services. Any PEIM that wants to allocate (as opposed to borrow) *should* 
> >> fail,
> unless
> >> it uses the PEI memory services. And if a PEIM wants to *borrow* (as 
> >> opposed to
> >> allocate), then it shouldn't need to scan HOBs.
> >>>>
> >>>> * If there is a requirement in the PI spec that the HOBs be produced
> >>>> on the S3 path as well, then I guess we'll have to comply with that.
> >>>> With my current understanding though, I feel that producing the same
> >>>> set of HOBs would give other PEIMs an incorrect view of memory
> >>>> ownership. The result of
> >>>>
> >>>>   all system memory HOBs minus all allocation HOBs
> >>>>
> >>>> would appear as
> >>>>
> >>>>   memory that is free for further allocation
> >>>>
> >>>> which would be false.
> >>>>
> >>>> * So my proposal would be to allow the platform to advertize a range for 
> >>>> CpuMpPei
> to
> >> borrow from, with two new PCDs.
> >>>>
> >>>> If you are strongly opposed to that, then I guess I can write a patch 
> >>>> for OvmfPkg
> >> that, on the S3 resume path, produces one (1) system memory HOB as an 
> >> *exception*,
> >> specifically to allow CpuMpPei's scanning to succeed (with an appropriate 
> >> code
> comment
> >> of course). I could also cover the entire area in question with a memory 
> >> allocation
> HOB
> >> as well, hoping that it would keep away other PEIMs that look for "free 
> >> memory",
> like
> >> in (a). Something like:
> >>>>
> >>>>   //
> >>>>   // Allow CpuMpPei to borrow memory from this range for the AP startup
> >>>>   // code, but prevent other PEIMs from thinking the range is "free
> >>>>   // memory".
> >>>>   //
> >>>>   AddMemoryRangeHob (0, BASE_512KB + BASE_128KB);
> >>>>   BuildMemoryAllocationHob (0, BASE_512KB + BASE_128KB,
> >>>>     EfiBootServicesData);
> >>>>
> >>>> Actually, let me try that, and see where I land.
> >>>>
> >>>> Thanks,
> >>>> Laszlo
> >>>>
> >>>>
> >>>>> -----Original Message-----
> >>>>> From: Laszlo Ersek [mailto:[email protected]]
> >>>>> Sent: Thursday, July 07, 2016 2:52 AM
> >>>>> To: Fan, Jeff; Kinney, Michael D; Justen, Jordan L
> >>>>> Cc: Paolo Bonzini; edk2-devel-01
> >>>>> Subject: Re: [edk2] multiprocessing in PEI?
> >>>>>
> >>>>> On 07/06/16 19:08, Laszlo Ersek wrote:
> >>>>>> Hi Jeff,
> >>>>>>
> >>>>>> On 07/05/16 15:50, Fan, Jeff wrote:
> >>>>>>> When CPU MP PPI installed, CPU MP PPI Services will be fully usable.
> >>>>>>
> >>>>>> I included CpuMpPei in OVMF, and it works fine on the normal boot path.
> >>>>>> (I haven't done anything special with it thus far, just built it
> >>>>>> into the firmware, and it starts up fine.)
> >>>>>>
> >>>>>> However, on the S3 resume path, it runs into an assertion failure:
> >>>>>> the
> >>>>>> GetWakeupBuffer() function fails. That is actually expected, because
> >>>>>> at that point the runtime OS being resumed owns all memory under 1MB.
> >>>>>>
> >>>>>> On the S3 resume path, OVMF does install a tiny bit of permanent PEI
> >>>>>> RAM: 32 KB in size (PcdS3AcpiReservedMemorySize), starting at 8288
> >>>>>> KB (PcdS3AcpiReservedMemoryBase). On the normal boot path, we
> >>>>>> reserve this area as AcpiNVS type memory, so that the runtime OS stays 
> >>>>>> out of
> it.
> >>>>>>
> >>>>>> Is CpuMpPei meant to be used on the S3 resume path in general?
> >>>>>
> >>>>> It looks like CpuMpPei expects memory resource descriptor HOBs to exist 
> >>>>> on the S3
> >> resume path as well. Then it seems to lay the wakeup buffer over OS-owned 
> >> memory
> under
> >> 1MB. But, it saves the original memory contents into a backup buffer 
> >> allocated from
> >> permanent PEI RAM. And, at end-of-PEI, the memory contents are restored.
> >>>>>
> >>>>> OVMF does not produce memory / IO / MMIO resource descriptors on the S3 
> >>>>> resume
> >> path. The assumption is that no PEIM will directly look for any such HOBs 
> >> on the S3
> >> path, only use the permament PEI RAM for memory allocation. Does this 
> >> conflict with
> the
> >> PI spec?
> >>>>>
> >>>>> I wonder if GetWakeupBuffer()'s scanning of EFI_RESOURCE_SYSTEM_MEMORY 
> >>>>> descriptor
> >> HOBs is a good idea. When it finds a location that is suitable as a wakeup 
> >> buffer,
> it
> >> "claims" that area by building a memory allocation HOB that covers the 
> >> area. I think
> >> that's fine; however, the scanning itself does not consider any other 
> >> memory
> allocation
> >> HOBs that may have been carved out of system memory by other PEIMs, 
> >> earlier.
> >>>>>
> >>>>> I wonder if platforms would be better served by a (base, size) pair of 
> >>>>> PCDs. The
> >> platform could set these PCDs, and make sure that both the OS and other 
> >> firmware
> >> modules (PEIMs and DXE drivers) stay out of this area. (For example, if S3 
> >> is not
> >> supported or enabled on the platform, then the platform could allocate 
> >> this area as
> >> Boot Services Data.
> >>>>> Otherwise, it would be AcpiNVS.) CpuMpPei could then remove the
> >>>>> resource HOB scanning, and it would only need to validate if (a) the
> >>>>> size PCD was big enough to contain the wakeup buffer, and (b) the
> >>>>> base PCD was low enough to keep the wakeup buffer under 1MB, (c) any
> >>>>> necessary alignments. Basically, ask the platform to preallocate the
> >>>>> wakeup buffer. (The minimal suitable size can be found statically, by
> >>>>> trial and
> >>>>> error.) The backup buffer (in permanent PEI RAM) could also be dropped,
> decreasing
> >> footprint.
> >>>>>
> >>>>> What do you think?
> >>>>>
> >>>>> Thanks
> >>>>> Laszlo
> >>>>>
> >>>>
> >>>
> >

_______________________________________________
edk2-devel mailing list
[email protected]
https://lists.01.org/mailman/listinfo/edk2-devel

Reply via email to