PC-DOS's predecessor, 86-DOS, was allegedly reverse engineered from CP/M. The subsequent lower development costs probably account for at least some of the price difference between the two products.
CP/M was (mostly) written in the PL/M language and ran on the 8-bit 8080/Z80 processors. 86-DOS was written in pure assembly language and ran on the 16-bit 8086 processor. Tim Paterson, its author, wrote an 8086 assembler and an 8080-to-8086 source code translator that ran on a CP/M machine. He used these tools to bootstrap 86-DOS.
86-DOS was intentionally designed to mimic the CP/M APIs to make it easy to port CP/M applications to 86-DOS through mechanical translation of the source code.
(And, surprise surprise, much of the business software that was available for IBM PC-DOS in the first couple of years were direct ports of existing CP/M applications: SuperCalc, WordStar, dBase II, etc.)
> CP/M was (mostly) written in the PL/M language and ran on the 8-bit 8080/Z80 processors. 86-DOS was written in pure assembly language and ran on the 16-bit 8086 processor.
In CP/M-80 1.x, most of the OS was written in PL/M. By the time we get to CP/M-80 2.x, the core of the OS (BDOS) has been rewritten in assembler for improved speed, while utilities (such as PIP) remain in PL/M.
CP/M-68K was written in C (although possibly with an earlier version in Pascal???). CP/M-8000 was written in C, probably ported from CP/M-68K.
CP/M-86 was mostly written in assembler, possibly with some bits (especially utilities) in PL/M and/or C as well.
And CP/M copied from DEC's operating systems, most especially RT/11.
I haven't examined the code myself, but the source code to the original PC-DOS is available and can be compared with CP/M. I've been told they were not copies.
Tim Paterson, of Seattle Computer Products and later Microsoft, gave a good talk at VCF West 2019 where he describes the history of 86-DOS (licensed to become PC-DOS and MS-DOS). There was an intention for significant API compatibility with CP/M, but no code was taken from CP/M.